第33講 数独(ナンバープレイス)問題解決ソフトVer.4の制作
(数独(ナンバープレイス)問題作成ソフトに挑戦する人は☆☆)

第8話 
Ver.7コード解説その6=部分構造解析行部分解説その3

                                                         if(b[i][y]>0){

                                                                 for(j=0;j<b[i][y];j++){

                                                                         if(rlst[i][y][j]==a[x][y]){

                                                                                 w=rlst[i][y][b[i][y]];

                                                                                 rlst[i][y][b[i][y]]=a[x][y];

                                                                                 rlst[i][y][j]=w;

                                                                                 break;

                                                                         }

                                                                 }

                                                         }

では、交換を行っています。
何の交換かお分かりですか。

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

赤いセルに7が入力される前は、
このセルのリストは、2,7,8,9でした。
7をリストから外すために7と9の交換をしているのです。
交換では、リストは2,9,8,7と順番が変わっただけで意味がないように見えるかもしれませんが、直前のところで
                                                 h1[g][i]=0;

                                                 if(lst[i][y][a[x][y]-1]==0){

                                                         lst[i][y][a[x][y]-1]=1;

                                                         b[i][y]--;

                                                         h1[g][i]=1;

b[i][y]が1減らされていて、3となっています。
3個がリスト数なので、結局2,9,8,7最初の3つだけがリストされ、7をリストから外すことに成功します。

具体的には

のリストは交換前は
b[4][0][0]=2,b[4][0][1]=7,b[4][0][2]=8,b[4][0][3]=9
だったのが、交換後は
b[4][0][0]=2,b[4][0][1]=9,b[4][0][2]=8,b[4][0][3]=7
です。しかし、b[i][y]=3なら、すべてがリストに入っているのでは?



実は、b[i][y]はリスト数ではなく、それに1を加えたものです。
b[i][y]=リスト数+1なのです。
えっ、どうして?
全体構造解析のエンジン部分をもう一度見てください。
      void zentaikouzoukaiseki(){
         register char i1,i2,i3,i4;
         char i1s,i2s;

         for(i1=0;i1<9;i1++){
           for(i2=0;i2<9;i2++){
              if(a[i1][i2]==0){
                for(i3=0;i3<9;i3++){
                  lst[i1][i2][i3]=0;
                }
                for(i3=0;i3<9;i3++){
                  if(a[i1][i3]>0)lst[i1][i2][a[i1][i3]-1]=1;
                }
                for(i3=0;i3<9;i3++){
                  if(a[i3][i2]>0)lst[i1][i2][a[i3][i2]-1]=1;
                }
                i1s=i1/3;
                i2s=i2/3;
                for(i3=0;i3<3;i3++){
                  for(i4=0;i4<3;i4++){
                    if(3*i1s+i3!=i1 && 3*i2s+i4!=i2 && a[3*i1s+i3][3*i2s+i4]>0)lst[i1][i2][a[3*i1s+i3][3*i2s+i4]-1]=1;
                  } 
                }
                for(i3=0;i3<9;i3++){
                  if(lst[i1][i2][i3]==0){
                    rlst[i1][i2][b[i1][i2]]=i3+1;
                      b[i1][i2]++;
                    }
                  }

                  if(b[i1][i2]==1){
                    iz[chs]=i1;
                    jz[chs]=i2;
                    chs++;
                  }
                }
              }
            }
          }
リスとした後に、b[i1][i2]は1足されています。
後から足している理由は、lst[i1][i2][i3]i3から始まるからです。
添え字が0から始まるので、rlst[i1][i2][b[i1][i2]]=i3+1;となっているのです。

したがって、交換後実際のリストになるは
lst[4][0][0]=2,lst[4][0][1]=9,lst[4][0][2]=8,lst[4][0][3]=7
濃紺の部分でだけで、7をリストから外すことに成功しています。
lst[4][0][3]=7を消滅さてもよかったのですが、試行がうまくいかなかったとき、
元に戻すためにデータを残しておくのです。





第7話へ 第9話へ


戻る

VC++講義第1部へ
vb講義へ
VB講義基礎へ
初心者のための世界で一番わかりやすいVisual C++入門基礎講座
初心者のための世界で一番わかりやすいVisual Basic入門基礎講座
初心者のための世界で一番わかりやすいVBA入門講義(基礎から応用まで)