森の小道


9

悲惨なカヌーに乗った後、川の急流の終わりに滝から落ちてしまいました。あなたのカヌーは爆発しましたが、あなたはなんとか爆発を生き延びました。しかし、あなたの川の旅は完全に地図から外れました-あなたは今、森の真ん中で迷いました。幸い、あなたはまだプログラミングスキルを持っているので、プログラムをツリーの側面に切り分けて、森を抜ける方法を見つけることにしました。ただし、ツリーには表面積があまりないため、プログラムをできるだけ短くする必要があります。

フォレストは、nby nn > 5)の正方形の文字で表すことができ、小文字のみで構成されますa-z。フォレストの例:

anehcienwlndm
baneiryeivown
bnabncmxlriru
anhahirrnrauc
riwuafuvocvnc
riwnbaueibnxz
hyirorairener
ruwiiwuauawoe
qnnvcizdaiehr
iefyioeorauvi
quoeuroenraib
cuivoaisdfuae
efoiebnxmcsua

このフォレストでは、a左上隅から右下隅に向かって斜めに文字のラインが走っていることにお気づきかもしれません。これは、森を通る「道」であり、それをたどるとどこかにあなたを導きます。あなたの仕事は、特異な経路を見つけるプログラムを書くことです。ここで、この課題で「パス」を意味するものをより具体的に説明します。

この課題での「パス」は、ブレゼンハムアルゴリズムで生成された可能性があるものに類似したラインとして定義されますが、次の追加要件があります。

  • 行の長さは6文字以上にする必要があります
  • 行内の同一直線上にある(完全に隣接する)文字のグループはすべて同じ長さでなければなりません
  • フォレストの一方の端で始まり、反対の端で終わります(詳しくは、私のコメントを参照しください)

2番目の要件をより明確に説明するには、次の行を検討してください。

aaa
   aaa
      aaa
         aaa
            aaa

この行は、同一線上にある文字の「セグメント」で構成されており、各セグメントは正確に3文字です。パスとみなされます。今、この行を考えてみましょう:

a
 aa
   a
    aa
      a
       aa

この行は、すべて同じ長さの文字ではない同一線上の「セグメント」で構成されています(一部は1文字で、一部は2文字です)。したがって、これはパスとしての資格はありません。

フォレストのマップが与えられたプログラムは、パスで使用されている文字を識別します。入力は、都合のよいもの(たとえば、コマンドライン引数、STDIN prompt()など)を使用します。変数に事前初期化することはできません。入力の最初の部分は、nフォレストのサイズを表す単一の整数です(フォレストは常に正方形です)。その後はスペースで、次にフォレスト全体が単一の文字列になります。たとえば、サンプルのフォレストは、次のように入力として提示されます。

13  anehcienwlndmbaneiryeivownbnabncmxlriruanhahirrnraucriwuafuvocvncriwnbaueibnxzhyirorairenerruwiiwuauawoeqnnvcizdaiehriefyioeorauviquoeuroenraibcuivoaisdfuaeefoiebnxmcsua

この出力は次のようになります。

a

パスは文字を使用して形成されているためaです。フォレスト内のパスは1つだけです。これはコードゴルフなので、最低数のキャラクターが勝ちます。質問がある場合は、コメント欄で質問してください。


複数のパスがある場合はどうなりますか?
Eric Tressler、2014

@EricTressler特定のフォレストにはパスが1つだけ存在します。それを反映するように仕様を編集します。
アブサン

パス文字はパスに属していない別の場所で使用できますか?
マーティンエンダー2014

例のフォレストにはおそらくそれが含まれています。サンプルフォレストのこの行の最初のaは、パスanhahirrnraucに含まれていません
Spade

@MartinBüttnerはい。しかし、それらはいつでも同じ文字から作成された2つのパスにはなりません。
アブサン

回答:


3

APL(ダイアログ14)(70)

⎕ML←3⋄Z/⍨1=≢¨Z←∪¨(↓⍉F),(↓F),{(⍳≢⍵)⌷¨↓⍵}¨(⊂F),⊂⌽F←⊃{⍵⍴⍨2/⍎⍺}/I⊂⍨' '≠I←⍞

説明:

  • ⎕ML←3:に設定MLすると3APL2の意味になります。
  • I←⍞:キーボードから行を読み取って保存します I
  • I⊂⍨' '≠IIスペースで分割
  • {... }/:この関数を2つの結果の文字列に適用します。
    • 2/⍎⍺:左の引数を評価して2回複製し、行列のサイズを与える
    • ⍵⍴⍨:そのサイズを使用して正しい引数をフォーマットする
  • F←⊃:開梱してに保存しFます。
  • {(⍳≢⍵)⌷¨↓⍵}¨(⊂F),⊂⌽F:双方の各行から:対角線を取得Fし、⌽F(垂直ミラーリングF)、Xは、その行番号列X、で値を取得します
  • (↓⍉F),(↓F),:行と列を取得する F
  • Z←∪¨:各行、列、対角線の一意の値を見つけて、に格納しますZ

「フォレスト」は長方形であるため、有効なパスがある場合、これらの1つはパス文字である1文字のみで構成されます。

  • Z/⍨1=≢¨ZZ要素が1つしかないサブアレイを取得します。

これにより、すべての有効なパスの文字が表示されますが、関係ないのは1つだけであるためです。


4

Lua- 506380-バイト

よく考えられたチャレンジの応募がなかったのがちょっと残念だったので、一緒に投げました。パスがあなたが与えた情報から持っていなければならない最小の識別可能なプロパティが何であるかを推測するのはとても楽しいことでした。私はそれが正しくできていれば幸いです...そして正しく実装しました

a=io.read"*l"n=a:match("%d+")+0 m=a:match"[a-z]+"o=""for i=1,n do for k=1,n^2,n do o=o..m:sub(i+k-1,i+k-1)end end q={m,o}for g=1,n^2 do for u=1,2 do l=q[u]:sub(g,g)for r=1,n do i=1 t=0 e=0 while i do s,e=q[u]:find(l:rep(r),e+1)if s then x=s-(e-s)-i-1 print(s,i,r,n,r)if x==n or x==n-2 or t==0 then t=t+1 i=s end else i=nil end end if t*r==n then print(l)os.exit()end end end end

以下でテストできます:

lua divisorPath.lua "input"

ワイルドなチャレンジャーが現れた場合、私はコードに価値があるかどうかを調べます。

更新:私たちより上に上がる人々を称えてゴルフをしました。その間、コードを右から左に進む認識されたパスに修正する必要がありました。おっとっと。


3

MATLAB-270文字

次の関数xは、フォレスト文字列を引数として受け入れ、指定されたルールに従ってフォレストを通過する有効な「パス」を表す文字を返す関数を定義しています。

function F=x(s),A=sscanf(s,'%d%s');n=A(1);A=reshape(A(2:end),n,n);for c=A(:)',B=A==c;for i=1:n,if~mod(n,i),C=[kron(eye(i),ones(n/i,1)),zeros(n,n-i)];for j=0:n-i,f=@(B)sum(sum(B&circshift(C,[0,j]))==n;D=fliplr(B);if f(B)|f(B')|f(D)|f(D'),F=char(c);end;end;end;end;end;end

非縮小バージョンは

function F = x(s)
    A = sscanf( s, '%d %s' );
    n = A(1);
    A = reshape( A(2:end), n,n );
    for c = A(:)'
        B = A==c;
        for i = 1:n
            if ~mod( n, i )
                C = [kron( eye(i), ones( n/i,1 ) ), zeros( n,n-i )];
                for j = 0:n-i
                    f = @(B) sum(sum( B & circshift( C, [0 j] ))) == n;
                    D = fliplr(B);
                    if f(B) | f(B') | f(D) | f(D')
                        F = char(c);
                    end
                end
            end
        end
    end
end

基本的な前提は、考えられるすべての有効なパスに対してブールマスクを作成し、行列のインデックス関数がすべてのマスクをカバーする文字を返すことです。これを実現するために、垂直または上から下のバックスラッシュ形状のマスクのみが作成されますが、フォレストマトリックスは、アイデンティティ、フリップ、90°回転、フリップ90°回転の4つの方向すべてで比較されます。

関数はすべてに対して実行されますn。コマンドラインで呼び出される例は次のとおりです

x('13 anehcienwlndmbaneiryeivownbnabncmxlriruanhahirrnraucriwuafuvocvncriwnbaueibnxzhyirorairenerruwiiwuauawoeqnnvcizdaiehriefyioeorauviquoeuroenraibcuivoaisdfuaeefoiebnxmcsua')

ans =

    a

3

Pythonの- 384 325 275

このアルゴリズムは基本的に、マトリックスの最初と最後の行を照合して文字が一致するかどうかを確認し、各線分の長さを計算します

012345
------
aaVaaa|0
aaVaaa|1
aaaVaa|2
aaaVaa|3
aaaaVa|4
aaaaVa|5

上記の例
では、最初の行のVはインデックス2にあり、最後の行のVはインデックス4にあります。
したがって、各ラインセグメントの長さはn /(4-2)+1 = 2で、n = 6になります。 。

次に、その行が有効かどうかを確認します。

左から右へのパスを見つけるために、行を列と入れ替え、同じことをもう一度行います。

編集: 270に到達できません(Pythonとくぼみインデントをくそー!!)

n,m=raw_input().split()
n,r=int(n),range
t=r(n)
a=[m[i:i+n]for i in r(0,n*n,n)]
for v in a,["".join([a[i][j]for i in t])for j in t]:
 for i in t:
  for j in t:
   p=1-2*(j-i<0);d,c=p*(j-i)+1,v[0][i]
   if 6<=sum([v[z][i+(z/(n/d))*p*(n%d==0)]==c for z in t])==n:print c;exit()
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.