poj 3074 Sudoku

来源:互联网 发布:php表格修改 编辑:程序博客网 时间:2024/05/29 04:35

坑爹的数独呀!又是搜索,又是剪枝~~~

代码如下:

#include<iostream>#include<stdio.h>#include<string.h>const int MAX_COLOUMN=81+9*9+9*9+9*9+2;const int MAX_ROW=81*9+2;int cnt[MAX_COLOUMN];int most,coloumn;bool ans[MAX_ROW];struct Point{int up,down,left,right;int coloumn;int row;}node[MAX_ROW*MAX_COLOUMN+MAX_COLOUMN];void init(int m){int i;for(i=0;i<m;i++){node[i].down=i;node[i].up=i;node[i].coloumn=i;node[i].left=i-1;node[i].right=i+1;cnt[i]=0;}node[0].left=m;node[m].right=0;}void remove (int c){node[node[c].right].left=node[c].left;node[node[c].left].right=node[c].right;int t,tt;for(t=node[c].down;t!=c;t=node[t].down){for(tt=node[t].right;tt!=t;tt=node[tt].right){cnt[node[tt].coloumn]--;node[node[tt].down].up=node[tt].up;node[node[tt].up].down=node[tt].down;}}}void resume(int c){int t,tt;for(t=node[c].up;t!=c;t=node[t].up){for(tt=node[t].left;tt!=t;tt=node[tt].left){cnt[node[tt].coloumn]++;node[node[tt].up].down=tt;node[node[tt].down].up=tt;}}node[node[c].right].left=c;node[node[c].left].right=c;}bool dfs(int k){int i,j;if(k>=most) return false;if(node[coloumn].right==coloumn){if(k<most)most=k;return true;}int t=coloumn+1;int c;for(i=node[coloumn].right;i!=coloumn;i=node[i].right){if(cnt[i]<t){c=i;t=cnt[i];if(t==1) break;}}remove(c);for(i=node[c].down;i!=c;i=node[i].down){for(j=node[i].right;j!=i;j=node[j].right){remove(node[j].coloumn);}ans[node[j].row]=true;if(dfs(k+1)){return true;}ans[node[j].row]=false;for(j=node[j].left;j!=i;j=node[j].left){resume(node[j].coloumn);}}resume(c);return false;}bool graph[MAX_ROW][MAX_COLOUMN];void addrow(int i,int j,int k){int curr=(i*9+j)*9+k;graph[curr][(i*9+j)]=true;graph[curr][81+i*9+k]=true;graph[curr][81+81+j*9+k]=true;int tr=i/3;int tc=j/3;graph[curr][81+81+81+(tr*3+tc)*9+k]=true;}char str[MAX_ROW];int main(){int N,M,i,j,k;while(scanf("%s",str)!=EOF){if(strcmp(str,"end")==0) break;N=81*9;M=9*9+9*9+9*9+9*9;coloumn=M;int cur=coloumn+1;init(coloumn);memset(graph,0,sizeof(graph));for(i=0;i<9;i++)for(j=0;j<9;j++){if(str[i*9+j]=='.'){for(k=0;k<9;k++){addrow(i,j,k);}continue;}k=str[i*9+j]-'1';addrow(i,j,k);}for(i=0;i<N;i++){int start=cur;int pre=cur;for(j=0;j<M;j++){if(graph[i][j]){int pos=j;node[cur].up=node[pos].up;node[node[pos].up].down=cur;node[cur].down=pos;node[pos].up=cur;cnt[pos]++;node[cur].coloumn=pos;node[cur].left=pre;node[pre].right=cur;node[cur].right=start;node[start].left=cur;node[cur].row=i;pre=cur++;}}}most=N+1;memset(ans,false,sizeof(ans));dfs(0);for(i=0;i<81;i++)for(j=0;j<9;j++)if(ans[i*9+j]){printf("%d",j+1);break;}printf("\n");}return 0;}