POJ 3074 Sudoku 解题报告(Dancing Link)

来源:互联网 发布:日本三菱材料数据造假 编辑:程序博客网 时间:2024/06/05 08:33
Sudoku
Time Limit: 1000MS Memory Limit: 65536KTotal Submissions: 7878 Accepted: 2792

Description

In the game of Sudoku, you are given a large 9 × 9 grid divided into smaller 3 × 3 subgrids. For example,

.2738..1..1...6735.......293.5692.8...........6.1745.364.......9518...7..8..6534.

Given some of the numbers in the grid, your goal is to determine the remaining numbers such that the numbers 1 through 9 appear exactly once in (1) each of nine 3 × 3 subgrids, (2) each of the nine rows, and (3) each of the nine columns.

Input

The input test file will contain multiple cases. Each test case consists of a single line containing 81 characters, which represent the 81 squares of the Sudoku grid, given one row at a time. Each character is either a digit (from 1 to 9) or a period (used to indicate an unfilled square). You may assume that each puzzle in the input will have exactly one solution. The end-of-file is denoted by a single line containing the word “end”.

Output

For each test case, print a line representing the completed Sudoku puzzle.

Sample Input

.2738..1..1...6735.......293.5692.8...........6.1745.364.......9518...7..8..6534.......52..8.4......3...9...5.1...6..2..7........3.....6...1..........7.4.......3.end

Sample Output

527389416819426735436751829375692184194538267268174593643217958951843672782965341416837529982465371735129468571298643293746185864351297647913852359682714128574936

Source

Stanford Local 2006

    解题报告: Dancing Link论文上的题目,按照论文上的矩阵构造方法构造,套Dancing Link模板即可。
    对于不能确定的位置,填充0-9,对于确定的位置,仅加入该数字。可以直接在输入串上记录答案,最后输出即可。代码如下:
#include <cstdio>#include <cstring>#include <iostream>#include <algorithm>using namespace std;const int M=1024*110;const int N=1024;int l[M], r[M], d[M], u[M], col[M], row[M], h[N], control[N];int dcnt = 0;char str[111];inline void addnode(int &x){++x;r[x]=l[x]=u[x]=d[x]=x;}inline void insert_row(int rowx, int x){r[l[rowx]]=x;l[x]=l[rowx];r[x]=rowx;l[rowx]=x;}inline void insert_col(int colx, int x){d[u[colx]]=x;u[x]=u[colx];d[x]=colx;u[colx]=x;}void dlx_init(int cols){memset(h, -1, sizeof(h));memset(control, 0, sizeof(control));dcnt=-1;addnode(dcnt);for(int i=1;i<=cols;++i){addnode(dcnt);insert_row(0, dcnt);}}void remove(int c){l[r[c]]=l[c];r[l[c]]=r[c];for(int i=d[c];i!=c;i=d[i])for(int j=r[i];j!=i;j=r[j]){u[d[j]]=u[j];d[u[j]]=d[j];control[col[j]]--;}}void resume(int c){for(int i=u[c];i!=c;i=u[i])for(int j=l[i];j!=i;j=l[j]){u[d[j]]=j;d[u[j]]=j;control[col[j]]++;}l[r[c]]=c;r[l[c]]=c;}bool DLX(int deep){if(r[0]==0){puts(str);return true;}int min=M, tempc;for(int i=r[0];i!=0;i=r[i]) if(control[i]<min){min=control[i];tempc=i;}remove(tempc);for(int i=d[tempc];i!=tempc;i=d[i]){str[row[i]/9]=row[i]%9+'1';for(int j=r[i];j!=i;j=r[j]) remove(col[j]);if(DLX(deep+1)) return true;for(int j=l[i];j!=i;j=l[j]) resume(col[j]);}resume(tempc);return false;}inline void insert_node(int x, int y){control[y]++;addnode(dcnt);row[dcnt]=x;col[dcnt]=y;insert_col(y, dcnt);if(h[x]==-1)h[x]=dcnt;elseinsert_row(h[x], dcnt);}int main(){#ifdef ACM//freopen("in.txt", "r", stdin);#endifwhile(~scanf("%s", str) && strcmp(str, "end")!=0){dlx_init(4*9*9);for(int i=1;i<=9;i++) for(int j=1;j<=9;j++){for(int k=1;k<=9;k++) if(str[(i-1)*9+(j-1)]=='.' || str[(i-1)*9+(j-1)]=='0'+k){int rr=(i-1)*9*9+(j-1)*9+(k-1);insert_node(rr, 81*0+(i-1)*9+k);insert_node(rr, 81*1+(j-1)*9+k);insert_node(rr, 81*2+((i-1)/3+(j-1)/3*3)*9+k);insert_node(rr, 81*3+(i-1)*9+j);}}DLX(0);}}

0 0
原创粉丝点击