状态压缩 HDU 1565
多组数据
给你一个n*n的矩阵
不能相邻的取数 上下左右
求最大的和
#include<stdio.h> #include<algorithm> #include<string.h> using namespace std; int n; int z[30][30]; int dp[2][1<<20+1],cnt; //dp和滚动数组差不多 推出的行只有相邻的有关系 int num[20000]; //用来记录 合法的状态 就是同行要不相邻 int main() { cnt=0; for(int i=0;i<(1<<20);i++) if((i&(i<<1))==0) num[cnt++]=i; while(scanf("%d",&n)!=EOF) { for(int i=0;i<n;i++) for(int j=0;j<n;j++) scanf("%d",&z[i][j]); memset(dp,0,sizeof(dp)); int len=(1<<n); for(int i=0;i<n;i++) { int p=i&1; //奇数偶数 for(int j=0;j<cnt;j++) { if(num[j]>=len) break; int sum=0; for(int k=0;k<n;k++) //和这个状态都是1 可以取 { if((num[j]&(1<<k))) sum+=z[i][k]; } int m1=0; for(int k=0;k<cnt;k++) { if(num[j]>=len) break; if(!(num[j]&num[k])) //上面最大的合法的状态转移过来 m1=max(m1,dp[1-p][num[k]]); } dp[p][num[j]]=sum+m1; //本行加上面的 } } int p=(n-1)&1; //最后奇偶 int ans=0; for(int i=0;i<len;i++) //最大的状态 ans=max(dp[p][i],ans); printf("%d\n",ans); } return 0; }
posted on 2016-12-03 14:44 HelloWorld!--By-MJY 阅读(150) 评论(0) 编辑 收藏 举报