poj 1185 状态压缩DP
2014-07-18 19:53
232 查看
思路:首先做个预处理,把每一行可以放的状态存起来,以后就可以只看这么多状态而不是for全看一遍了。
之后,因为放一个可以影响四个方向2格,所以第i行的状态和i-1行i-2行有关系的,通过之前的状态来推,状态转移方程可以写为:
dp[i][j][k]=max(dp[i][j][k],dp[i-1][k][l]+f[i][j])
这里i代表第i行,j为第i行的状态,k为第i-1行状态,l为i-2行状态,f[i][j]表示第i行在j状态下放的个数。
记得前两行特殊处理下。
这里直接开数组会MLE,所以用滚动数组来。
之后,因为放一个可以影响四个方向2格,所以第i行的状态和i-1行i-2行有关系的,通过之前的状态来推,状态转移方程可以写为:
dp[i][j][k]=max(dp[i][j][k],dp[i-1][k][l]+f[i][j])
这里i代表第i行,j为第i行的状态,k为第i-1行状态,l为i-2行状态,f[i][j]表示第i行在j状态下放的个数。
记得前两行特殊处理下。
这里直接开数组会MLE,所以用滚动数组来。
#include<iostream> #include<cstdio> #include<cstring> #include<map> #include<vector> #include<string> #include<algorithm> #include<queue> using namespace std; char a[111][15]; int f[111][1025]; int dp[3][1025][1025]; int m,n; vector<int>g[111]; void pre() { int l=(1<<m); for(int i=0;i<n;i++) { for(int j=0;j<l;j++) { int cnt=-1; int r=j; bool flag=0; int num=0; for(int k=0;k<=m;k++) { if(r%2) { if(cnt!=-1&&cnt<2) { flag=1; break; } if(a[i][k]=='H') { flag=1; break; } num++; cnt=0; } else if(cnt!=-1)cnt++; r/=2; } if(flag==0) { g[i].push_back(j); f[i][j]=num; } } } } void solve() { if(n==1) { int ans=0; for(int i=0;i<g[0].size();i++)ans=max(ans,f[0][g[0][i]]); printf("%d\n",ans); } else { int ans=0; memset(dp,0,sizeof(dp)); int x=g[0].size(); int y=g[1].size(); int z; for(int i=0;i<x;i++) { for(int j=0;j<y;j++) { if((g[0][i]&g[1][j])==0) { dp[0][g[1][j]][g[0][i]]=max(dp[0][g[1][j]][g[0][i]],f[0][g[0][i]]+f[1][g[1][j]]); ans=max(ans,dp[0][g[1][j]][g[0][i]]); } } } for(int i=2;i<n;i++) { x=g[i].size(); y=g[i-1].size(); z=g[i-2].size(); for(int j=0;j<x;j++) { for(int k=0;k<y;k++) { if(g[i][j]&g[i-1][k])continue; for(int l=0;l<z;l++) { if(g[i][j]&g[i-2][l])continue; if(g[i-1][k]&g[i-2][l])continue; dp[1][g[i][j]][g[i-1][k]]=max(dp[1][g[i][j]][g[i-1][k]],dp[0][g[i-1][k]][g[i-2][l]]+f[i][g[i][j]]); ans=max(ans,dp[1][g[i][j]][g[i-1][k]]); } } } for(int j=0;j<x;j++) { for(int k=0;k<y;k++) { dp[0][g[i][j]][g[i-1][k]]=dp[1][g[i][j]][g[i-1][k]]; } } memset(dp[1],0,sizeof(dp[1])); } printf("%d\n",ans); } } int main() { scanf("%d%d",&n,&m); for(int i=0;i<n;i++)scanf("%s",a[i]); pre(); solve(); return 0; }
相关文章推荐
- poj 1185 压缩状态dp
- poj 1185 & hdu 4539(状态压缩DP)
- poj1185——状态压缩DP
- POJ 1185 HDU 4539 状态压缩DP
- POJ 1185 炮兵阵地[状态压缩DP]
- [状态压缩DP] Poj 3254, Poj 1185
- poj1185 炮兵阵地 经典状态压缩dp
- POJ 1185 炮兵阵地 (状态压缩DP)
- poj 1185 炮兵阵地 状态压缩dp
- 状态压缩DP总结【POJ3254】【POJ1185】【POJ3311】【HDU3001】【POJ2288】【ZOJ4257】【POJ2411】【HDU3681】
- POJ 1185 炮兵阵地 状态压缩(DP)
- POJ 1185 炮兵阵地 状态压缩DP简单题
- poj1185 炮兵阵地 状态压缩dp
- poj 1185 炮兵阵地 (状态压缩dp)
- 状态压缩dp入门题 POJ 1185 炮兵阵地
- poj 1185 炮兵阵地 //状态压缩DP
- POJ 1185 炮兵阵地 (状态压缩,DP,附测试数据)
- poj 1185 炮兵阵地 状态压缩DP
- POJ - 1185 跑兵阵地 状态压缩DP
- POJ 1185 炮兵阵地 状态压缩DP