题目:数独。填充大小为1x1,4x4,9x9数独。
分析:搜索。直接利用dfs回溯求解。存储每行,每列,每个子块的数字使用情况,优化搜索。
说明:对于解有顺序要求,DL超时了 - -。
#include <cstring>
#include <cstdio>
int data[9][9];
int b_id[9][9];
int visit_r[10][10];
int visit_c[10][10];
int visit_b[10][10];
int position[81];
int dfs(int k, int size, int n)
{
if (k == size) {
return 1;
}
int p = position[k];
int r = p/(n*n), c = p%(n*n), b = r/n*n + c/n;
for (int v = 1; v <= n*n; ++ v) {
if (!visit_r[r][v] && !visit_c[c][v] && !visit_b[b][v]) {
visit_r[r][v] = 1;
visit_c[c][v] = 1;
visit_b[b][v] = 1;
data[r][c] = v;
if (dfs(k+1, size, n)) {
return 1;
}
visit_r[r][v] = 0;
visit_c[c][v] = 0;
visit_b[b][v] = 0;
}
}
return 0;
}
int main()
{
int n, t = 0;
while (~scanf("%d",&n)) {
if (t ++) {
printf("\n");
}
for (int i = 0; i < n*n; ++ i) {
for (int v = 1; v <= n*n; ++ v) {
visit_r[i][v] = 0;
visit_c[i][v] = 0;
visit_b[i][v] = 0;
}
}
int size = 0;
for (int i = 0; i < n*n; ++ i) {
for (int j = 0; j < n*n; ++ j) {
scanf("%d",&data[i][j]);
b_id[i][j] = i/n*n + j/n;
if (data[i][j] == 0) {
position[size ++] = i*n*n + j;
}else {
visit_r[i][data[i][j]] = 1;
visit_c[j][data[i][j]] = 1;
visit_b[b_id[i][j]][data[i][j]] = 1;
}
}
}
if (dfs(0, size, n)) {
for (int i = 0; i < n*n; ++ i) {
for (int j = 0; j < n*n; ++ j) {
if (j) {
printf(" ");
}
printf("%d",data[i][j]);
}
printf("\n");
}
}else {
printf("NO SOLUTION\n");
}
}
return 0;
}