MENU

【VB】ペントミノ3Dパズルを解く(9)終わりに

この連載をお読みいただきありがとうございました。
3Dは2D版を拡張すれば簡単にできるだろうとタカをくくっていましたが、前述のように鏡映の判断に手間取りなかなか納得のいく状態になりませんでした。ここで紹介した方法以外にいい方法があれば、ぜひ教えていただきたいと思っています。

・鏡映とは

鏡映とはその名前のとおり鏡に映ったようなもの同士の関係のことです。鏡映の関係にある2つの解はペントミノでは同一の解と見なしますので、どちらか一方は捨てることになります。


鏡映の関係にある2つの解の一方を捨てる方法として最初に思いつくのは「新しい解が見つかったとき、それまで見つかった解の中に新しい解と鏡映の関係にあるものを探して、見つかったらその解は捨てる」という方法です。しかしこの方法には時間がかかります。解を完成させたあとで鏡映の判断をしているからです。解を完成させる前に鏡映の判断ができれば、その未完成の解はあっさり捨てて次の探索に進むことができるので全体の探索時間が短縮できます。

・部品の位置で判断(1)

鏡映を途中で判断するには「1つの部品(例えば部品"P")に着目し、その部品が置かれたときに箱のどこに置かれたかで鏡映を判断する」方法があります。その部品が箱の半分より手前にあれば解、奥側にあれば捨てるというような方法です(例えば画像のカーキ色の部品"P"は箱の中心線(点線)よりも手前にあるので解とします)。


プログラムでは部品"P"を判定用に使いました。部品"P"や部品"F"は180度回転で重なるものを除外して部品棚(Shelfクラス)を作ると、棚には XY, YZ, ZX の各平面に平行な部品が2個ずつ残ります。このような部品はそれぞれの平面に対する鏡映の判断ができます。DEFクラスの定数(SynonymJudgePieceName)を"P"から"F"に変更しても同じ結果が得られます(探索時間は"P"よりもかなり遅くなります)。

・部品の位置で判断(2)

部品"P"が箱の真ん中のときはどうしたらいいのでしょうか。画像のように手前と奥のちょうど真ん中に部品"P"があるときです。このようなときは他の部品を使って判断します。その部品もまたちょうど真ん中にあるときは ・・・ というようなケースも想定していくと、すべての部品がリストになっている部品棚(Shelves)の順序を使うのが妥当だということになります。今回のプログラムでは DEFクラス で部品棚を"F", "I", "L", ・・・ の順に作っているので、その順番に評価していきます。


鏡映面は XY, YZ, ZX の3方向にあるので、部品"P"の向きによってそれぞれの鏡映面で判断することになります。

・3Dの絵を描く

以上で3Dペントミノの説明は終わりですが、実はプログラムの説明より3Dの絵を描くのが大変でした。AUTODESKのTinkercadというフリーソフトを使って描いたのですが初めてなのでものすごく時間がかかりました。

  1. 絵にしたい部品のパターンをプログラムで画面に表示させる
  2. 市販の3Dペントミノ商品(かつのう)で実際に組み立てる
  3. Tinkercad内で実物どおりに部品を作って組み立て画面をコピー
  4. エクセルに貼り付け破線等のオートシェイプで体裁を整え再度画面をコピー
  5. Paint.netで画像のサイズ等を調整し保存
  6. ブログに投稿

Tinkercadについては教育機関で主に使われているようで、とにかく簡単で使いやすいという印象です。インストールの必要もなく動作も軽快です。私のような「空間認識能力」に問題がある者が使うにはちょうどいいレベルでお勧めのソフトです。

・次回予告

今回のような箱詰めパズルに「手古鶴」という木製のものがあります。20年以上前に購入したものですが、残念ながら1回も完成させることができませんでした。次回はこのパズルにプログラムで挑戦してみたいと思います。