数独

【问题背景】

There is really only one rule:
Fill in the grid so that
every row,
every column, and
every 3 x 3 box
contains the digits 1 through 9.
这个游戏只有一个规则:
将格子填满使得每一行,每一列,和每一个小的九宫格恰好包含1-9这9个数字,正是由于规则简单
而又变化多端,数独一时间风靡全球。现在,我们希望你能编写一个程序解决数独问题。
【输入数据】
输入数据一共9行,每行有9个字符。
输入数据描述了一个待解决的数独,其中,“?”表示数独中的空缺。
我们的输入数据总保证有唯一解。
【输出数据】
输出一共9行,每行9个数字,表示你的答案。
【样例输入】
5????7??6
?6????5?4
?834?????
???182?4?
??1???9??
?7?369???
?????543?
1?5????9?
7??2????1
【样例输出】
514927386
967831524
283456179
659182743
321574968
478369215
892615437
135748692
746293851

解析:

初始化判断各种点可以填的数字,

1-9

SDK(i,j,k) 第i,j个点是否可以填k

若可以,SDKTRUE(i,j,k)在该点填上k,

若之后判断中,错误,回溯,SDKFALSE(i,j,k).

  1 Var
  2   i,j:integer;
  3   z,y:integer;
  4   ch:Char;
  5   b:Array[1..9,1..9] of integer;
  6   a:Array[1..9,1..9] of Char;
  7   h:Array[1..9,0..9] of Boolean; //1~9hang,0..9
  8   L:Array[1..9,0..9] of Boolean; //1~9Lie, 0..9
  9   x:Array[1..9,0..9] of BooLean; //LU-->RD,0..9
 10 Procedure SDKTrue(i,j,xx:Integer);
 11   Begin
 12     h[i,xx]:=True;
 13     l[j,xx]:=True;
 14     if (i in [1..3]) Then
 15       Begin
 16         if j in [1..3] Then x[1,xx]:=True
 17         Else if j in [4..6] Then x[2,xx]:=True
 18         Else x[3,xx]:=True;
 19       End
 20     Else
 21       if (i in [4..6]) Then
 22         Begin
 23           if j in [1..3] Then x[4,xx]:=True
 24           Else if j in [4..6] Then x[5,xx]:=True
 25           Else x[6,xx]:=True;
 26         End
 27     Else
 28       Begin
 29         if j in [1..3] Then x[7,xx]:=True
 30         Else if j in [4..6] Then x[8,xx]:=True
 31         Else x[9,xx]:=True;
 32       End;
 33   End;
 34 Procedure SDKFalse(i,j,xx:Integer);
 35   Begin
 36     h[i,xx]:=False;
 37     l[j,xx]:=False;
 38     if (i in [1..3]) Then
 39       Begin
 40         if j in [1..3] Then x[1,xx]:=False
 41         Else if j in [4..6] Then x[2,xx]:=False
 42         Else x[3,xx]:=False;
 43       End
 44     Else
 45       if (i in [4..6]) Then
 46         Begin
 47           if j in [1..3] Then x[4,xx]:=False
 48           Else if j in [4..6] Then x[5,xx]:=False
 49           Else x[6,xx]:=False;
 50         End
 51     Else
 52       Begin
 53         if j in [1..3] Then x[7,xx]:=False
 54         Else if j in [4..6] Then x[8,xx]:=False
 55         Else x[9,xx]:=False;
 56       End;
 57   End;
 58 Function SDK(i,j,xx:integer):Boolean;
 59   Begin
 60     if h[i,xx] Then Exit(True);
 61     if l[j,xx] Then Exit(True);
 62     if (i in [1..3]) Then
 63       Begin
 64         if (j in [1..3]) Then
 65           Begin
 66             if (x[1,xx]) Then Exit(True)
 67             Else Exit(False);
 68           End
 69         Else if (j in [4..6]) Then
 70           Begin
 71             if (x[2,xx]) Then Exit(True)
 72             Else Exit(False);
 73           End
 74         Else if (x[3,xx]) Then Exit(True);
 75       End
 76     Else
 77       if (i in [4..6]) Then
 78         Begin
 79           if (j in [1..3]) Then
 80             Begin
 81               if (x[4,xx]) Then Exit(True)
 82               Else Exit(False)
 83             End
 84           Else if (j in [4..6]) Then
 85             Begin
 86               if (x[5,xx]) Then Exit(True)
 87               Else Exit(False);
 88             End
 89           Else if (x[6,xx]) Then Exit(True)
 90         End
 91     Else
 92       Begin
 93         if (j in [1..3]) Then
 94           Begin
 95             if (x[7,xx]) Then Exit(True)
 96             Else Exit(False);
 97           End
 98         Else if (j in [4..6]) Then
 99           Begin
100             if (x[8,xx]) Then Exit(True)
101             Else Exit(False);
102           End
103         Else if (x[9,xx]) Then Exit(True)
104       End;
105     Exit(False);
106   End;
107 Procedure Find_SDK(Var x,y:integer);
108   Var
109     i,j:integer;
110   Begin
111     For i:=1 to 9 do
112       For j:=1 to 9 do
113         if b[i,j]=0 Then
114           Begin
115             x:=i;
116             y:=j;
117             Exit;
118           End;
119     x:=0; y:=0; Exit;
120   End;
121 Function Making_SudoKu(i,j:integer):Boolean;
122   Var
123     k,x,y:Integer;
124     Flag:Boolean;
125   Begin
126     Flag:=False;
127     For k:=1 to 9 do
128       if Not SDK(i,j,k) Then
129         Begin
130           //Writeln(i,' ',j,' ',k);
131           Flag:=True;
132           SDKTrue(i,j,k);
133           b[i,j]:=k;
134           Find_SDK(x,y);
135           if (x=0) and (y=0) Then Exit(True);
136           if Not Making_SudoKu(x,y) Then
137             Begin
138               b[i,j]:=0;
139               SDKFALSE(i,j,k);
140               Flag:=False;
141             End
142           Else Exit(True);
143         End;
144     if Not Flag Then Exit(False);
145     Exit(True);
146   End;
147 Begin
148   Assign(input,'sudoku.in');
149   ReSet(Input);
150   Assign(Output,'sudoku.out');
151   ReWrite(Output);
152   For i:=1 to 9 do
153     Begin
154       For j:=1 to 9 do
155         Begin
156           Read(a[i,j]);
157           if a[i,j] in ['1'..'9'] Then
158             Begin
159               b[i,j]:=Ord(a[i,j])-48;
160               h[i,b[i,j]]:=True;
161               l[j,b[i,j]]:=True;
162               if (i in [1..3]) Then
163                 Begin
164                   if j in [1..3] Then x[1,b[i,j]]:=True
165                   Else if j in [4..6] Then x[2,b[i,j]]:=True
166                   Else x[3,b[i,j]]:=True;
167                 End
168               Else
169                 if (i in [4..6]) Then
170                   Begin
171                     if j in [1..3] Then x[4,b[i,j]]:=True
172                     Else if j in [4..6] Then x[5,b[i,j]]:=True
173                     Else x[6,b[i,j]]:=True;
174                   End
175               Else
176                 Begin
177                   if j in [1..3] Then x[7,b[i,j]]:=True
178                   Else if j in [4..6] Then x[8,b[i,j]]:=True
179                   Else x[9,b[i,j]]:=True;
180                 End;
181             End;
182         End;
183       Readln;
184     End;
185  { For i:=1 to 9 do
186     Begin
187       For j:=1 to 9 do
188         Write(b[i,j]);
189       Writeln;
190     End; }
191   For i:=1 to 9 do
192     For j:=1 to 9 do
193       if b[i,j]=0 Then
194         Begin
195           if Making_Sudoku(i,j) Then
196           For z:=1 to 9 do
197             Begin
198               For y:=1 to 9 do
199                 Write(b[z,y]);
200               Writeln;
201             End
202           Else Writeln(-1);
203           Close(input);
204           Close(output);
205           Exit;
206         End;
207   For z:=1 to 9 do
208     Begin
209       For y:=1 to 9 do
210         Write(b[z,y]);
211       Writeln;
212     End;
213   Close(input);
214   Close(Output);
215 End.

 

posted @ 2012-11-04 15:46  Iris.Catch-22.S、`  阅读(318)  评论(0编辑  收藏  举报