ASCIIで織る


12

|文字の長方形のグリッドが、織機のピンと張ったストリングス(縦糸)を表し、他の糸(横糸)を表すと想像してください-

7×4織機の不織布ワープは次のとおりです。

|||||||
|||||||
|||||||
|||||||

緯糸を経糸に織り込む方法はいくつかありますが、最も簡単なのは平織りです。

平織りの最初の行では、緯糸は最初のたて糸ストリングの上から始まり、2番目のストリングの下、3番目のストリングの上、4番目の下などに続きます。

2番目の横糸の行は最初の横糸の行と同じですが、1本の縦糸によって右にオフセットされているため、下から始まり、上に行く、というように続きます。

7×4織機では、平織りは次のようになります。

-|-|-|-
|-|-|-|
-|-|-|-
|-|-|-|

緯糸は経糸を1回、次に1回未満通過し、後続の各行は1ストリング右にシフトされると言うことで、平織りを説明できます。

一般化された織りは、緯糸を縦にv回、次にu回、それぞれの行を右にs文字列シフトすることで説明できます。(すべての値は整数であり、sは 0または負であってもよい、U及びVは非負でなければなりません。)

v = 1u = 2s = 2ツイル織りのタイプの7×4織機:

-||-||-
||-||-|
|-||-||
-||-||-

チャレンジ

あなたの仕事は、vus、織機の幅と高さ、および初期シフトを与えられたバーとダッシュの織りパターンを生成する最短のプログラム(バイト単位)を書くことです。

最初のシフトは、緯糸の最初の行は、右(上記の例では0)にシフトされた文字列の数です。後続の各行は、さらにs個の文字列だけシフトされます。

プログラムは、これらの6つの数値を使いやすい形式(stdin、関数呼び出しなど)で取得し、バーと長方形の編まれたグリッドをstdoutに出力する必要があります。すべての入力が有効であると想定できます。(すべての値は整数で、幅と高さは正である必要があります。初期シフトは何でもかまいません。)

幅= 5、高さ= 4、初期シフト= 0、v = 1、u = 3、s = -2:

-|||-
||-||
-|||-
||-||

幅= 5、高さ= 4、初期シフト= 3、v = 1、u = 3、s = -2:

|||-|
|-|||
|||-|
|-|||

幅= 5、高さ= 4、初期シフト= 1、v = 1、u = 1、s = 0:

|-|-|
|-|-|
|-|-|
|-|-|

幅= 5、高さ= 4、初期シフト= 0、v = 1、u = 0、s = 0:

-----
-----
-----
-----

ノート

  • パターンは常に、グリッドの左上隅の縦糸上の横糸から始まります(最初にシフトされていない場合)。
  • すべての横糸が左から入ります。彼らこのようにらせん状ではありません
  • u + vは必ずしもグリッド幅の倍数ではありません。
  • uvの両方が0でない場合があります

回答:


5

ルビー、72バイト

w,h,v,u,s,i=$*.map &:to_i;h.times{puts ((?-*v+?|*u)*w)[-i%(u+v),w];i+=s}

これについて多くを語ることはありません。との繰り返しを1つ作成-|、それをw何回か繰り返し(念のため)、各行の適切なセクションを切り取ります。


u + v == 1の場合、w倍で十分ですか?
edc65 14

@ edc65はい%(u+v)。この場合、私は今までindexから始めているだけな0のでw、文字列に文字が残っています。
マーティンエンダー14

3

JavaScript(ES 6)128

F=(w,h,i,v,u,s)=>{for(x=('-'[R='repeat'](v)+'|'[R](u))[R](w*h),l=v+u,i=-i%l+l,s=-s%l+l;h--;i+=s)console.log(x.substr(i,w)+'\n')}

テスト

F(11,8,2,5,3,-2)

||-----|||-
-----|||---
---|||-----
-|||-----||
||-----|||-
-----|||---
---|||-----
-|||-----||

2

Python、92バイト

w,h,i,v,u,s=eval(A)
x=('|'*u+'-'*v)*w
while h:print(x[-i:]+x[:-i])[-w:];x=x[-s:]+x[:-s];h-=1

うーん...だから今ルビーを学びたいと思った。

「幅、高さ、初期シフト、v、u、s」の形式で文字列変数を割り当てて入力します。
プログラムの前に貼り付けます:

A="80,80,0,2,2,-9"

1
私はそれがあるべきだと信じていますwhile h。私は余分な行を取得しています。
カルビンの趣味14

1
任意の入力形式システムを使用する必要があります-入力値をコンマで区切って評価します。
isaacg 14

1

JavaScript(ES6)、111バイト

機能的なArray.fromを使用した、わ​​ずかに異なるES6アプローチ。

f引数(w,h,i,v,u,s)を取り、文字列を返します。コードに追加された改行および文字列内のリテラル改行は\n、明確にするために置き換えられました。どちらもバイトカウントに反映されません。

f=(w,h,i,v,u,s)=>(A=Array).from(A(h),(_,j)=>A.from(A(w),
(_,k)=>(j*((x=v+u)-s)+x+k-i)%x<v?'-':'|').join``).join`\n`

使用法

console.log(f(5,4,0,1,3,-2)) /*

-|||-
||-||
-|||-
||-||

*/

説明付きのゴルフバージョン

Arrayのエイリアスを作成することで、バイトを節約しましたが、これは非ゴルフバージョンには反映されていません。

// take input and create an array of length h (height):
f = (w,h,i,v,u,s) => Array.from( Array(h),

    // in each row position j, create an array of length w (width):
    (_,j) => Array.from( Array(w), 

        // in each cell, place - or | depending on the pattern (i,v,u,s)
        // and current position (j,k):
        (_,k) => ( j * ( ( x = v + u ) - s ) + x + k - i ) % x < v ? '-' : '|'

    // turn each row into a string:
    ).join``

// join rows with newlines:
).join`\n`

0

C、357バイト

#include<stdio.h>
int w,h,t,v,u,s,i,j,l,f;int main(){scanf("%d %d %d %d %d %d",&w,&h,&t,&v,&u,&s);l=v+u;char g[l];g[l]='\0';f=0;while(u--){g[v+u]='|';}while(v--){g[v]='-';}for(i=0;i<h;i++){for(j=0;j<w;j++){printf("%c",g[abs(t+f+j)%l]);}printf("\n");f-=s;}}

「見た目より快適です。」「そうでなければならない。」-GiaとEidon(誰もこの参照を取得しません。ヒント:「織りマット」)

だから、私は今、約5時間これに取り組んでいますが、あきらめます。このコードを機能させる方法がわかりません。最初の行の後も逆方向に進み、その後完全に間違っています(7 4 0 2 2 1)。

より簡単に読むことができるシンプルなバージョンを次に示します。入力を取得し、テンプレート配列を作成して、ループ内で印刷するだけです。

#include<stdio.h>
int w,h,t,v,u,s,i,j,l,f;
int main(){
    scanf("%d %d %d %d %d %d",&w,&h,&t,&v,&u,&s);
    l=v+u;char g[l];g[l]='\0';f=0;
    while(u--){g[v+u]='|';}while(v--){g[v]='-';}
    for(i=0;i<h;i++){
        for(j=0;j<w;j++){
            printf("%c",g[abs(t+f+j)%l]); // THIS is the line that needs help.
        }
        printf("\n");
        f-=s;
    }
}

ここで簡単にテストできます。http//www.compileonline.com/compile_c_online.phpを使用して、下部の[STDIN入力]ボックスで「7 4 0 1 1 1」を使用します。数字の編集を開始すると、問題が表示されます。

申し訳ありませんが、実用的な解決策を思い付きませんでした。これが嫌いです。他の人に修正を依頼するためにアップロードしないように時間を費やしすぎました。

私はしばらくの間、このprintfを使用して、一番上の行(簡単な)を残りの行(問題のある行)にさらに分離しています。 printf("%c",g[i?abs(t+f+j)%l:abs(t+j)%l]);


for(i=0;i++<h;)?2番目のforループでも同じトリックですか?ただし、ループごとに1文字しか保存されません。
11684 14

私はそれを数回試しましたが、それは数字をオフにし、それらを使用する方法を見つけることができませんでした。
ネス14

奇妙な。他の方法で?++i?しかし、それはただ暗闇の中でのショットです。
11684 14

いや; これは、数値が比較に使用される前に増加し、最終的にh-1回の繰り返しになります。forループ宣言の2番目のセクションで++を使用する場合の問題は、ループ内で使用する前にiがインクリメントされることです。オフナンバーを扱うには、数学のどこかに-1が必要な場合があり、そのためショートカットはそれだけの価値はありません。これが-1なしで実行可能でない限り。まだわかりません。
ネス14

もちろん!手のひらを顔に当てます
11684 14

0

Haskell、126バイト

f w h i v u s=putStr.unlines$take h$take w<$>(iterate(drop(mod s(u+v)))$drop(mod(-i)(u+v)).cycle$('-'<$[1..v])++('|'<$[1..u]))

1
些細なゴルフは変更になるf w h i v u sため(w?h)i v u s。挿入機能
-H.PWiz
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.