POJ 3074 Sudoku (数独,Dancing Links 精确覆盖)

POJ3074

**做的Dancing Links 练习:** [http://vjudge.net/contest/view.action?cid=47185#overview](http://vjudge.net/contest/view.action?cid=47185#overview)   3\*3的数独, 转化为精确覆盖的过程也比较容易理解。 行是N\*N\*N 行,列是4\*N*N 列。  

Sudoku

Time Limit: 1000MS

Memory Limit: 65536K

Total Submissions: 7940

Accepted: 2822

Description

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

.

2

7

3

8

.

.

1

.

.

1

.

.

.

6

7

3

5

.

.

.

.

.

.

.

2

9

3

.

5

6

9

2

.

8

.

.

.

.

.

.

.

.

.

.

.

6

.

1

7

4

5

.

3

6

4

.

.

.

.

.

.

.

9

5

1

8

.

.

.

7

.

.

8

.

.

6

5

3

4

.

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

527389416819426735436751829375692184194538267268174593643217958951843672782965341
416837529982465371735129468571298643293746185864351297647913852359682714128574936

Source

Stanford Local 2006

模板题。

/* ***
Author :kuangbin
Created Time :2014/5/30 11:46:50
File Name :E:\2014ACM\专题学习\DLX\POJ3074.cpp
************************************************ */

#include <stdio.h>

#include <string.h>

#include

#include

#include

#include

#include

#include

#include

#include <math.h>

#include <stdlib.h>

#include <time.h>
using namespace std;
const int N = 9; //33数独
const int MaxN = N\
N*N + 10;
const int MaxM = N*N*4 + 10;
const int maxnode = MaxN4 + MaxM + 10;
char g[MaxN];
struct DLX
{
int n,m,size;
int U[maxnode],D[maxnode],R[maxnode],L[maxnode],Row[maxnode],Col[maxnode];
int H[MaxN],S[MaxM];
int ansd,ans[MaxN];
void init(int _n,int _m)
{
n = _n;
m = _m;
for(int i = 0;i <= m;i++)
{
S[i] = 0;
U[i] = D[i] = i;
L[i] = i-1;
R[i] = i+1;
}
R[m] = 0; L[0] = m;
size = m;
for(int i = 1;i <= n;i++)H[i] = -1;
}
void Link(int r,int c)
{
++S[Col[++size]=c];
Row[size] = r;
D[size] = D[c];
U[D[c]] = size;
U[size] = c;
D[c] = size;
if(H[r] < 0)H[r] = L[size] = R[size] = size;
else
{
R[size] = R[H[r]];
L[R[H[r]]] = size;
L[size] = H[r];
R[H[r]] = size;
}
}
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];
–S[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])
++S[Col[U[D[j]]=D[U[j]]=j]];
L[R[c]] = R[L[c]] = c;
}
bool Dance(int d)
{
if(R[0] == 0)
{
for(int i = 0;i < d;i++)g[(ans[i]-1)/9] = (ans[i]-1)%9 + ‘1’;
for(int i = 0;i < N
N;i++)printf(“%c”,g[i]);
printf(“\n”);
return true;
}
int c = R[0];
for(int i = R[0];i != 0;i = R[i])
if(S[i] < S[c])
c = i;
remove(c);
for(int i = D[c];i != c;i = D[i])
{
ans[d] = Row[i];
for(int j = R[i];j != i;j = R[j])remove(Col[j]);
if(Dance(d+1))return true;
for(int j = L[i];j != i;j = L[j])resume(Col[j]);
}
resume(c);
return false;
}
};
void place(int &r,int &c1,int &c2,int &c3,int &c4,int i,int j,int k)
{
r = (i*N+j)*N + k; c1 = i*N+j+1; c2 = N*N+iN+k;
c3 = N\
N*2+j*N+k; c4 = N*N*3+((i/3)*3+(j/3))N+k;
}
DLX dlx;
int main()
{
//freopen(“in.txt”,”r”,stdin);
//freopen(“out.txt”,”w”,stdout);
while(scanf(“%s”,g) == 1)
{
if(strcmp(g,”end”) == 0)break;
dlx.init(N\
N*N,N*N*4);
int r,c1,c2,c3,c4;
for(int i = 0;i < N;i++)
for(int j = 0;j < N;j++)
for(int k = 1;k <= N;k++)
if(g[i*N+j] == ‘.’ || g[i*N+j] == ‘0’+k)
{
place(r,c1,c2,c3,c4,i,j,k);
dlx.Link(r,c1);
dlx.Link(r,c2);
dlx.Link(r,c3);
dlx.Link(r,c4);
}
dlx.Dance(0);
}
return 0;
}

------ 本文结束------
  • 本文作者: kuangbin
  • 本文链接: 152.html
  • 版权声明: 本博客所有文章除特别声明外,均采用 CC BY-NC-SA 4.0 许可协议。转载请注明出处!
0%