グリッド充填蛇行を完了する


18

グリッド塗りつぶし蛇行は、正方形のグリッドのすべてのセルを少なくとも1訪問し、隣接するセル間のエッジを2回以上渡らず、それ自体を渡さない閉じたパスです。例えば:N×N

グリッドが満たされると、次の8つのタイルのいずれかでグリッドの各セルを表すことができます。

このように番号を付けると、上記の蛇行のタイルはこのマトリックスで表すことができます。

5 6 5 6
4 8 3 2
5 7 6 2
4 3 4 3

あなたの仕事は、タイルの不完全なセットを与えられたグリッド充填蛇行を完了することです。たとえば、不完全な蛇行:

... 0不足しているタイルに対してsを使用して表すことができます:

5 0 0 0 6
0 0 7 0 0
0 0 0 0 3
2 4 0 0 0
0 0 3 0 0

...このように完了することができます:

... ie:

5 6 5 1 6
4 8 7 6 2
5 7 7 7 3
2 4 8 8 6
4 1 3 4 3

仕様書

  • 入力には常に少なくとも、最大で(空ではない)タイルがあります。ここで、です。1N22N7
  • 回答で指定されている限り、任意の値セットを使用してタイルを表すことができます。
  • 入力と出力は、回答で指定されている限り、どのような形式と順序でもかまいません。
  • すべての入力に対して少なくとも1つの有効なソリューションが存在します(つまり、無効な入力を処理する必要はありません)。
  • 標準のI / Oルールが適用されます。
  • 標準的な抜け穴は禁止されています。
  • 「実用的な」言語であっても説明が奨励されます。

テストケース

入力(Θ):

0 6
0 0

出力(Θ):

5 6
4 3

入力(Θ):

5 6 5 6
4 0 3 2
5 7 6 2
4 3 4 3

出力(Θ):

5 6 5 6
4 8 3 2
5 7 6 2
4 3 4 3

入力(Θ):

5 0 0 0 6
0 0 7 0 0
0 0 0 0 3
2 4 0 0 0
0 0 3 0 0

出力(Θ):

5 6 5 1 6
4 8 7 6 2
5 7 7 7 3
2 4 8 8 6
4 1 3 4 3


1
@Arnauldあなたは正しいです。無効です。蛇行は単一の閉じた経路です。
ヨルダン

1
@Arnauldありがとう、その変更を加えました。このサイトでMathJaxが有効になっていることを知りませんでした!
ヨルダン

回答:


11

JavaScript(ES7)、 236 ...  193185 バイト

入力マトリックスを変更して出力します。

m=>(g=(d,x,y,v,r=m[y],h=_=>++r[x]<9?g(d,x,y,v)||h():r[x]=0)=>r&&1/(n=r[x])?x|y|!v?n?g(d='21100--13203-32-21030321'[n*28+d*3+7&31],x+--d%2,y+--d%2,v+=n<7||.5):h():!m[v**.5|0]:0)(0,0,0,0)

オンラインでお試しください!

(OPが提供する視覚化ツールと互換性のあるマトリックスとフラットリストの両方として結果を印刷するいくつかの後処理コードを含む)

結果

どうやって?

変数

gd x y vは、現在の方向、現在の座標および訪問されたセルの数をとる再帰関数です。d(x,y)v

次の変数ものスコープで定義されています:g

  • rは、マトリックスの現在の行です。

    r = m[y]
  • h1 8 g g 0は、現在のセルに対してからまでのすべての値を試行し、それぞれでを呼び出すヘルパー関数です。が成功するとすぐに停止するか、現在のセルを戻し18gg0、バックトラックする必要がある場合はます。

    h = _ => ++r[x] < 9 ? g(d, x, y, v) || h() : r[x] = 0

初期チェック

n

r && 1 / (n = r[x]) ? ... ok ... : ... failed ...

(0,0)v>0

x | y | !v ? ... no ... : ... yes ...

今のところ、出発点に戻っていないと仮定しましょう。

パスを探しています

n0h

n0

ndd

d = '21100--13203-32-21030321'[n * 28 + d * 3 + 7 & 31]

最後の8つのエントリは無効であり、省略されています。他の4つの無効なエントリは、ハイフンで明示的にマークされます。

参照用に、チャレンジで提供されるデコードされたテーブル、コンパス、タイルセットを以下に示します。

   | 1 2 3 4 5 6 7 8
---+-----------------
 0 | 0 - - 1 3 - 3 1          1
 1 | - 1 - - 2 0 2 0        0 + 2
 2 | 2 - 1 - - 3 1 3          3
 3 | - 3 0 2 - - 0 2

g1/2v781

g(d, x + --d % 2, y + --d % 2, v += n < 7 || .5)

dxy

パスの検証

(0,0)v>0

781/2v

v=N2v>N2v<N2kk=v

したがって、JSコード:

!m[v ** .5 | 0]

フォーマットされたソース

m => (
  g = (
    d,
    x, y,
    v,
    r = m[y],
    h = _ => ++r[x] < 9 ? g(d, x, y, v) || h() : r[x] = 0
  ) =>
    r && 1 / (n = r[x]) ?
      x | y | !v ?
        n ?
          g(
            d = '21100--13203-32-21030321'[n * 28 + d * 3 + 7 & 31],
            x + --d % 2,
            y + --d % 2,
            v += n < 7 || .5
          )
        :
          h()
      :
        !m[v ** .5 | 0]
    :
      0
)(0, 0, 0, 0)

よくやった。コードの説明を読みたいです。
ヨルダン

@Arnauldそれを強引に強制するか、別のアルゴリズムを使用しますか?
ジョナ

1
@ジョナ私は現在説明を書いています。基本的に、はい、それはブルートフォースアプローチですが、アルゴリズムは、ありとあらゆるボードを試すのではなく、何らかの矛盾が検出されるとすぐにバックトラックします。
アーナルド
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.