枚举第一行即可,与训练指南上例题相似
代码如下:
#include <cstdio> #include <cstring> int a[21][21],b[21][21],n,m; char s[25][25]; bool check_line(int x) { int ans=b[0][x]; if (x) ans+=b[0][x-1]; if (x<m-1) ans+=b[0][x+1]; if (ans==a[0][x] || ans+1==a[0][x]) return true; return false; } int g(int x,int y) { int ans=b[x][y]; if (x) ans+=b[x-1][y]; if (y) ans+=b[x][y-1]; if (y<m-1) ans+=b[x][y+1]; return ans; } bool f(int s) { for (int i=0; i<m; ++i) if (s & (1<<i)) b[0][i]=1; else b[0][i]=0; if (n==1) { for (int i=0; i<m; ++i) if (g(0,i)!=a[0][i]) return false; return true; } int i,j; for (i=0; i<m; ++i) if (!check_line(i)) return false; for (i=1; i<n; ++i) for (j=0; j<m; ++j) if (g(i-1,j)==a[i-1][j]) b[i][j]=0; else if (g(i-1,j)+1==a[i-1][j]) b[i][j]=1; else return false; for (i=0; i<m; ++i) if (g(n-1,i)!=a[n-1][i]) return false; return true; } int main() { int i,j,T,kcase=0; scanf("%d",&T); while (T--) { scanf("%d%d",&n,&m); getchar(); for (i=0; i<n; ++i) scanf("%s",s[i]); for (i=0; i<n; ++i) for (j=0; j<m; ++j) a[i][j]=s[i][j]-'0'; for (int s=0; s<(1<<m); ++s) if (f(s)) break; printf("Case %d:\n",++kcase); for (i=0; i<n; ++i) { for (j=0; j<m; ++j) if (b[i][j]) printf("*"); else printf("."); printf("\n"); } } return 0; }