#define_crt_secure_no_warnings#include<vector>#include<iostream>#include<cstring>using namespacestd;structnode{Node (intX1,inty1): X (x1), Y (y1) {}intx; inty; Node*Up ; Node*Down ; Node*Left ; Node*Right ;};classexactcover{ Public: Vector<int>Solveexactcover (); Exactcover (Vector<vector<BOOL>>&); Vector<int>Getans () {returnans; }Private: intM//Number of rows intN//Number of columnsnode*Mroot; Vector<Node*>Mcolumnloc; Vector<int>Mcolumncount; Vector<vector<Node*>>Mnodeloc; voidCoverint); voidUncover (int); Vector<int>ans; BOOLdfs ();}; Vector<vector<BOOL>> Suduko2exactcover (vector<vector<int>>& A, vector<vector<int>>&list) {Vector<vector<BOOL>>ret; intM =0; intN =Bayi*4; for(inti =0; I <9; i++) for(intj =0; J <9; J + +) { intSt =1; intEn =9; if(A[i][j]) st = en =A[i][j]; for(intK = st; K <= en; k++) {Auto TMP= vector<BOOL> (N,false); tmp[Bayi*0+ I *9+ K-1] =true; tmp[Bayi*1+ J *9+ K-1] =true; tmp[Bayi*2+ I *9+ j] =true; tmp[Bayi*3+ (I/3*3+ J/3) *9+ K-1] =true; Ret.push_back (TMP); List.push_back (Vector<int>{i, J, k}); } } returnret;}intMain () {intT; CIN>>T; while(t--) {Auto a= vector<vector<int>> (9, vector<int> (9,0)); Vector<vector<int>>list; for(inti =0; I <9; i++) for(intj =0; J <9; J + +) Cin>>A[i][j]; Auto Para=Suduko2exactcover (A, list); Exactcover Inst (para); Inst.solveexactcover (); Auto U=Inst.getans (); for(auto x:u) a[list[x][0]][list[x][1]] = list[x][2]; for(inti =0; I <9; i++) for(intj =0; J <9; J + +) cout<< A[i][j] << (j = =8?"\ n":" "); } return 0;}BOOLExactcover::d fs () {if(Mroot->right = = mroot)return true; Auto Visitedrow= vector<BOOL> (M,false); Auto P= mroot->Right ; intMinC =100000; intMiny =-1; Node* MINP =nullptr; while(P! =mroot) { if(Mcolumncount[p->y] <MinC) {MINP=p; Miny= p->y; MinC= mcolumncount[p->y]; } P= p->Right ; } if(!minc | | miny = =-1)return false; BOOLsolved =false; P= minp->Down ; Cover (Miny); while(P! =MINP) { intCurrentX = p->x; Ans.push_back (CurrentX); Auto Q= p->Right ; while(Q! =p) {cover (q-y); Q= q->Right ; } if(!solved)if(Dfs ())return true; Q= p->Left ; while(Q! =p) {Uncover (q-y); Q= q->Left ; } ans.pop_back (); P= p->Down ; } uncover (Miny); return false;} Vector<int>exactcover::solveexactcover () {DFS (); returnans;} Exactcover::exactcover (Vector<vector<BOOL>>&a) {ans.clear (); M=a.size (); if(! Mreturn; N= a[0].size (); Mcolumnloc= vector<node*>(N, nullptr); Mcolumncount= vector<int> (N,0); Mnodeloc= Vector<vector<node*>> (M, vector<node*> (N,0)); Mroot=NewNode (-1, -1); Vector<Node*>& cl =Mcolumnloc; Vector<vector<Node*>>& L =Mnodeloc; for(inti =0; i < N; i++) Cl[i] =NewNode (-1, i); Mroot->right = cl[0]; Mroot->left = Cl[n-1]; for(inti =0; i < N; i++) {Cl[i]->left = (i = =0? Mroot:cl[i-1]); Cl[i]->right = (i = = N-1? Mroot:cl[i +1]); } for(inti =0; i < M; i++) for(intj =0; J < N; J + +) if(A[i][j]) l[i][j] =NewNode (i, j); for(intj =0; J < N; J + +) {Auto P=Cl[j]; for(inti =0; i < M; i++) if(A[i][j]) {Mcolumncount[j]++; P->down =L[i][j]; L[I][J]->up =p; P=L[i][j]; } P->down =Cl[j]; CL[J]->up =p; } for(inti =0; i < M; i++) {Node* p =nullptr; Node* head =nullptr; for(intj =0; J < N; J + +) if(A[i][j]) {if(p = = nullptr) head = p =L[i][j]; Else{p->right =L[i][j]; L[I][J]->left =p; P=L[i][j]; }} P->right =Head; Head->left =p; }}voidExactcover::cover (intX) {Auto Head=Mcolumnloc[x]; Head->left->right = head->Right ; Head->right->left = head->Left ; Auto P= head->Down ; while(P! =head) {Auto H1=p; Auto Q= h1->Right ; while(Q! =H1) {Mcolumncount[q->y]--; Q->up->down = q->Down ; Q->down->up = q->Up ; Q= q->Right ; } P= p->Down ; }}voidExactcover::uncover (intX) {Auto Head=Mcolumnloc[x]; Head->left->right =Head; Head->right->left =Head; Auto P= head->Up ; while(P! =head) {Auto H1=p; Auto Q= h1->Left ; while(Q! =H1) {Mcolumncount[q->y]++; Q->up->down =Q; Q->down->up =Q; Q= q->Left ; } P= p->Up ; }}
Dancing links
There's a search on the internet.
Special note is to reverse the recovery.
I have to say Knuth's IQ is a little high.
But POJ on the 3074 TLE, I also defy, all kinds of stickers to say T data I was a second out, forget, ignore
Yesterday evening to today tangled a small mistake
If the member data in the class is not initialized, it may not be 0.
It took me two hours to make this little mistake.
"Hiho" Sudoku