通过条件约束模拟后续全状态+暴力枚举决定变量==不超时
{或者说,一边边求解一边判断正误以减少不必要的运算}
统一代码风格
1 #include<iostream> 2 #include<string.h> 3 #include<stdio.h> 4 using namespace std; 5 int f[4][2]={{0,-1},{0,1},{-1,0}}; 6 const int maxn=20; 7 int ans; 8 int addcha; 9 int cnt=0; 10 int a[maxn][maxn]; 11 bool check(int n) 12 { 13 int aa[maxn][maxn]; 14 for(int i=0;i<n;i++) 15 for(int j=0;j<n;j++) 16 aa[i][j]=a[i][j]; 17 addcha=0; 18 for (int i=0;i<n-1;i++) 19 { 20 for(int l=0;l<n;l++) 21 { 22 int num_of_1=0; 23 for(int j=0;j<3;j++)//枚举四个方向 24 { 25 int x=i+f[j][0];//表示行 26 int y=l+f[j][1];//表示列 27 if(x<0 || x>=n || y<0 || y>=n) continue;//千万不能忘了等号啊 28 num_of_1+=aa[x][y]; 29 } 30 int sx=num_of_1%2; 31 if (sx==aa[i+1][l]) continue; 32 if (aa[i+1][l]==1) return false;else {aa[i+1][l]=sx;addcha++;} 33 } 34 35 } 36 return true; 37 } 38 void dfs(int n,int x,int y,int t)//先逐个换第一行,暴力枚举 39 {//每次遇到新状态就求出是否满足条件 40 if(check(n))//判断满足条件 41 { 42 ans=min(ans,t+addcha); 43 } 44 if (x>=1) return; 45 if (a[x][y]==0) 46 { 47 {//将a[x][y]改为1 48 a[x][y]=1; 49 if(y==n-1) dfs(n,x+1,0,t+1); 50 else dfs(n,x,y+1,t+1); 51 a[x][y]=0; 52 if(y==n-1) dfs(n,x+1,0,t); 53 else dfs(n,x,y+1,t); 54 } 55 } 56 else 57 {//不改变a[x][y] 58 if(y==n-1) dfs(n,x+1,0,t); 59 else dfs(n,x,y+1,t); 60 } 61 62 } 63 int main() 64 { 65 //freopen("out.txt","w",stdout); 66 int k; 67 scanf("%d",&k); 68 for(int cas=1;cas<=k;cas++) 69 { 70 cnt=0; 71 int n; 72 scanf("%d",&n); 73 for(int i=0;i<n;i++) 74 for(int j=0;j<n;j++) 75 scanf("%d",&a[i][j]); 76 ans=10000; 77 dfs(n,0,0,0); 78 // cout<<"cnt="<<cnt<<endl; 79 printf("Case %d: ",cas); 80 if (ans==10000) printf("-1 ");else printf("%d ",ans); 81 } 82 return 0; 83 }