四子连棋——惨不忍睹的经历,这样一个题目做了两个中午
这个题目在CodeVS 上的数据更强,我的倒数第二个版本代码(十五分钟前版本)在洛谷的五个测试点全0ms 可是后来又微调了一下才通过Codevs 十一个测试点的第六个。
1 #include<map> 2 #include<set> 3 #include<queue> 4 #include<cmath> 5 #include<cstdio> 6 #include<vector> 7 #include<string> 8 #include<cstring> 9 #include<iostream> 10 #include<algorithm> 11 using namespace std; 12 const int ax[]={-1,1,0,0},ay[]={0,0,-1,1}; 13 string st[6]; 14 int ans=0x7fffffff,lim=1,sp[3][3]; 15 bool this_is_just_a_mark,flag,cap=true,code[180]; 16 bool dn(string x[6]){ 17 for(int i=0;i<4;i++){ 18 bool ln=true; 19 for(int j=0;ln&&j<4;j++) 20 if(x[i][j]!=x[i][0]) 21 ln=false; 22 if(ln)return true; 23 } 24 for(int j=0;j<4;j++){ 25 bool rw=true; 26 for(int i=0;rw&&i<4;i++) 27 if(x[i][j]!=x[0][j]) 28 rw=false; 29 if(rw)return true; 30 } 31 bool con1=true; 32 for(int i=0;con1&&i<4;i++) 33 if(x[i][i]!=x[0][0]) 34 con1=false; 35 if(con1)return true; 36 bool con2=true; 37 for(int i=0;con2&&i<4;i++) 38 if(x[i][3-i]!=x[0][0]) 39 con2=false; 40 return con2; 41 } 42 void dfs(string x[6],int s,int sp[3][3],bool pl){ 43 if(dn(x)){ 44 ans=min(ans,s); 45 flag=true;return; 46 } 47 if(flag)return; 48 if(s>lim)return; 49 for(int i=1;i<=2;i++) 50 for(int k=0;k<4;k++){ 51 int nx=sp[i][0]+ax[k],ny=sp[i][1]+ay[k],t1=sp[i][0],t2=sp[i][1]; 52 if(nx<0||nx>=4||ny<0||ny>=4||code[x[nx][ny]]!=pl)continue; 53 swap(x[t1][t2],x[nx][ny]); 54 sp[i][0]=nx;sp[i][1]=ny; 55 dfs(x,s+1,sp,!pl); 56 sp[i][0]=t1;sp[i][1]=t2; 57 swap(x[t1][t2],x[nx][ny]); 58 } 59 } 60 61 int main(){ 62 code['B']=true;code['W']=false; 63 for(int i=0;i<4;i++)cin>>st[i]; 64 for(int i=0;i<4;i++) 65 for(int j=0;j<4;j++) 66 if(st[i][j]=='O') 67 if(!this_is_just_a_mark)sp[1][0]=i,sp[1][1]=j,this_is_just_a_mark=true; 68 else sp[2][0]=i,sp[2][1]=j; 69 while(lim++){ 70 flag=false; 71 dfs(st,0,sp,false); 72 flag=false; 73 dfs(st,0,sp,true); 74 if(ans!=0x7fffffff){ 75 cout<<ans<<endl; 76 break; 77 } 78 } 79 return 0; 80 }
两个OJ 都是0ms 和1ms 通过。

浙公网安备 33010602011771号