アルゴリズム講座/入門編/多重ループ検索 ホームページへ戻る 目次へ戻る
パズル問題解法のアルゴリズム講座

入門編

多重ループ検索

 さて、次に「ライツアウト」に挑戦してみましょう。

1.巨大な多重ループでパターンを生成

   このパズルの重要な法則「押す順番は関係ない」ということから、前に述べたように「5×5=25個」の
   ボタンをそれぞれ押すか押さないかの2通りからの選択なので「2の25乗=33,554,432通り」
   パターンを調べることになりますが、
10
1112131415
1617181920
2122232425
 
    (1) ボタンの押す押さないを決めていく順番を右図とする。
    (2) その順番通りにボタンの名前(変数名)をa〜yとする。
    (3) 変数の値は、押す場合を1,押さない場合を0とする。
 
   とすると、次のようなプログラムが書けます。

      /* 全てのパターンを生成する */
      for (a=0; a < 2; a++)
       for (b=0; b < 2; b++)
        for (c=0; c < 2; c++)
         for (d=0; d < 2; d++)
          for (e=0; e < 2; e++)

                    (途中略)

                 for (x=0; x < 2; x++)
                  for (y=0; y < 2; y++) {


                    生成されたパターン通りにボタンを押す;

                    /* 結果の確認 */
                    if (全てのライトが消えていたら)
                        このパターンを記録する;

                    今のパターンでのボタン押しを元に戻す;

     }

   以上のような25重のfor文のループで全パターンを生成して解を求めることが出来ます。
   不明な物の個数分だけ、for文を重ねて記述すればよいのです。
   簡単なパズル問題なら大抵はこの方法で解を出すことが出来ます。(アルゴリズムの基本)
 

2.ところで、もっとうまい方法はないか?

   しかし、この方法だと前の実験の通り探索を終えるのに約30秒もかかってしまいます。
   結論から先に言うと「ライツアウト」の探索は、33,554,432通りも調べる必要はありません。
   それどころか、「たったの32通り」を調べるだけでよいのです。理由は簡単です。
 
    
     
     
    25
    (1) ボタンの押す押さないを決めていく順番は上の例と同じとする。
    (2) 最上段の5個のボタンの押すパターンを生成する。(2の5乗=32通り)
    (3) 2段目以降については、すぐ上の位置のライトの状態で選択の余地なく決定される。
 
      何故なら、右図の「6」の位置において、もし「1」の位置のライトがついていたら、
      今それを消しておかないと、もう「1」のライトを消すことが出来なくなります。
      逆に、もし「1」の位置のライトが消えていたら、今「6」を押して「1」をつけて
      しまうと、もう「1」のライトを消すことが出来なくなります。
      この現象が結局、最後の「25」まで続いてしまうのです。
 
    (4) そして、最下段の5個のライトが総て消えていれば、それが解となります。
 
 
   正式公開版の「ライツアウト」が瞬時に解を出す秘密はこれです。たった32通りを調べているだけなのです。
 
 
 
  (追記)ここで説明したアルゴリズムよりも、もっと面白い方法でライツアウトを解く方法があります。ここ



目次へ戻る   前の頁へ戻る  次の頁へ進む