hdu1565 状压DP做的
2014-07-26 16:09
197 查看
/****** 题意:从一个矩阵中选出一些数,选出的数不能相邻,求能选出的最大的和; 思路:状压DP 也可以用什么流做,不过现在不懂图论 *******/ #include <iostream> #include <cstring> #include <algorithm> #include <cstdio> #define INF 0xfffffff using namespace std; int dp[20][17777], a[20][20], cnt, s[1<<20], num1[20][17777], n; int num(int i, int k) { int ans = 0, j; for(j = 0; j < n; j++) if(k & (1 << j)) ans += a[i][j]; return ans; } bool can(int k) { if(k&(k<<1)) return false; return true; } void DP() { int i,j,k; memset(dp,0,sizeof(dp)); for(j=0;j<cnt;j++) dp[0][j]=num1[0][j]; for(i=1;i<n;i++) { for(j=0;j<cnt;j++) { for(k=0;k<cnt;k++) if((s[k]&s[j])==0) { dp[i][j]=max(dp[i][j],dp[i-1][k]+num1[i][j]); } } } } int main() { //freopen("input.txt","r",stdin); //freopen("outputh.txt","w",stdout); while(scanf("%d", &n) != EOF) { if(n == 0) { puts("0"); continue; } int i,j,k; cnt=0; for(i=0;i<n;i++) for(j=0;j<n;j++) scanf("%d", &a[i][j]); for(k=0;k<(1<<n);k++) if(can(k)) { s[cnt]=k; cnt++; } for(i = 0; i < n; i++) for(k=0;k<cnt;k++) num1[i][k]=num(i,s[k]); DP(); int ans=0; for(j=0;j<cnt;j++) ans=max(ans,dp[n-1][j]); printf("%d\n", ans); } return 0; }
相关文章推荐
- hdu1565(状压dp)
- hdu1565 状压dp
- hdu 1074 Doing Homework(状压DP)
- POJ 2686 Traveling by Stagecoach (状压DP)
- HDUOJ Clear All of Them I 状压DP
- HDU 3001 Travelling(状压DP)
- [BZOJ1725][Usaco2006 Nov]Corn Fields牧场的安排(状压dp)
- poj 2686 Traveling by Stagecoach(状压dp)
- bzoj 1688: [Usaco2005 Open]Disease Manangement 疾病管理(状压DP)
- Headmaster's Headache - UVa 10817 状压dp
- Travelling HDU-3001(3进制-状压dp)
- Codeforces 544E Remembering Strings 状压dp
- BZOJ 2734: [HNOI2012]集合选数( 状压dp )
- poj 3254 Corn Fields(状压dp)
- POJ3254 状压DP入门
- hdu 4352 XHXJ's LIS 状压数位dp
- Painting A Board(状压dp)
- UVa 11759 洛克人的难题 状压dp
- Codeforces Beta Round #8 C. Looking for Order 状压dp
- ZOJ 2994 && HDU 1992 Tiling a Grid With Dominoes (状压DP)