http://poj.org/problem?id=1185
状态压缩+dp
代码:
#include<iostream> #include<cstdio> #include<cstring> #include<string> #include<map> #include<set> #include<vector> #include<stack> #include<queue> #include<algorithm> #define LL long long #define ULL unsigned long long using namespace std; const int INF=0x3f3f3f3f; const int MOD=1000000007; const int N=105; const int M=205; char a[N][N]; int b[N],len; vector<int>vt[N]; vector<int>num[N]; int dp[N][M][M]; int ok(int x,int y) { len=0; while(y>0) { b[len++]=(y&1); y=y>>1; } int sum=0; for(int i=0;i<len;++i) if(b[i]==1) { ++sum; if((i-2>=0&&b[i-2]==1)||(i-1>=0&&b[i-1]==1)||(a[x][i]=='H')) return -1; } return sum; } int main() { //freopen("data.in","r",stdin); int n,m; while(scanf("%d %d ",&n,&m)!=EOF) { for(int i=0;i<=n;++i) {vt[i].clear();num[i].clear();} memset(a,0,sizeof(a)); for(int i=1;i<=n;++i) gets(a[i]); for(int i=1;i<=n;++i) for(int j=0;j<(1<<m);++j) { int k=ok(i,j); if(k==-1) continue; vt[i].push_back(j); num[i].push_back(k); } vt[0].push_back(0); num[0].push_back(0); memset(dp,-1,sizeof(dp)); for(unsigned int j=0;j<vt[1].size();++j) dp[1][0][j]=num[1][j]; for(int i=2;i<=n;++i) for(unsigned int j=0;j<vt[i-1].size();++j) for(unsigned int l=0;l<vt[i].size();++l) if((vt[i-1][j]&vt[i][l])==0) { for(unsigned int r=0;r<vt[i-2].size();++r) if((vt[i-2][r]&vt[i-1][j])==0&&(vt[i][l]&vt[i-2][r])==0&&dp[i-1][r][j]!=-1) { if(dp[i][j][l]==-1||dp[i][j][l]<dp[i-1][r][j]+num[i][l]) dp[i][j][l]=dp[i-1][r][j]+num[i][l]; } } int ans=0; for(unsigned int j=0;j<vt[n-1].size();++j) for(unsigned int l=0;l<vt[n].size();++l) if(dp[n][j][l]!=-1) ans=max(ans,dp[n][j][l]); printf("%d\n",ans); } return 0; }