LightOJ - 1011 Marriage Ceremonies(状压DP)
2015-10-27 22:35
363 查看
题目大意:给你N对男女的匹配的值,问如果配对,才能使每个男女只有一个配偶,且配对的和最大
解题思路:这题用二分图的最大权比配也可以做
我这边用的是DP,因为最多只有16个,所以可以压缩
用dp[i][j]表示第i个男的,女的配对情况是j的情况下的最大值
则dp[i + 1][j | (1 << k)] = max(dp[i][j] + val[i + 1][k])
解题思路:这题用二分图的最大权比配也可以做
我这边用的是DP,因为最多只有16个,所以可以压缩
用dp[i][j]表示第i个男的,女的配对情况是j的情况下的最大值
则dp[i + 1][j | (1 << k)] = max(dp[i][j] + val[i + 1][k])
#include <cstdio> #include <cstring> #include <algorithm> #include <queue> using namespace std; const int N = 20; const int M = (1 << 16) + 10; struct Node { int row, state; Node() {} Node(int row, int state): row(row), state(state) {} }; int val ; int dp [M]; int n, cas = 1; void init (){ scanf("%d", &n); for (int i = 0; i < n; i++) for (int j = 0; j < n; j++) scanf("%d", &val[i][j]); } void solve() { memset(dp, 0, sizeof(dp)); int all = (1 << n) - 1; queue<Node> Q; for (int i = 0; i < n; i++) { Q.push(Node(0, (1 << i))); dp[0][1 << i] = val[0][i]; } while (!Q.empty()) { int s = Q.front().state; int row = Q.front().row; Q.pop(); if (row == n - 1) continue; for (int i = 0; i < n; i++) { if (s & (1 << i)) continue; if (dp[row + 1][s | (1 << i)] < dp[row][s] + val[row + 1][i]) { dp[row + 1][s | (1 << i)] = dp[row][s] + val[row + 1][i]; Q.push(Node(row + 1, s | (1 << i))); } } } printf("Case %d: %d\n", cas++, dp[n - 1][all]); } int main() { int test; scanf("%d", &test); while (test--) { init(); solve(); } return 0; }
相关文章推荐
- SQL Server设置登录验证模式
- 利用KMP求周期串思路
- 1027课堂知识大纲整理
- 从头认识java-4.7 构造器初始化(1)
- 20151027项目收尾管理、知识产权管理及法律法规
- 胖虎谈ImageLoader框架(一)
- 范围判断in 和not in
- UE4制作插件的插件神器
- C malloc free 函数实现
- eclipse启动tomcat弹出错误提示:Tomcat setting should be set in tomcat preference page
- 微信分享自定义图片标题摘要
- lintcode 中等题:4 Sum 四个数之和
- Ajax各代技术
- MyEclipse web developemnt with Maven
- new AlertDialog.Builder(this).setxx引发的胡思乱想
- 结构型模式之对象适配器
- MongoDB Ubuntu安装 APP 支付宝微信支付
- iOS中文网址路径转换URLEncode
- matlab绘制带有吴茶邦(error)的分组柱状图
- qt tr utf8 无法编译通过 常量中有换行符