PKU 2288 Islands and Bridges 状态dp
题意:
给你一张地图,上面有一些岛和桥。你要求出最大的三角哈密顿路径,以及他们的数量。
哈密顿路:一条经过所有岛的路径,每个岛只经过一次。
最大三角哈密顿路:满足价值最大的哈密顿路。
价值计算分为以下三部分:
1. 所有点权的和。
2. 对于路径上任意两个连续的点(共享一条边)的点权乘积的和。
3. 对于路径上任意三个连续的点,如果他们构成一个三角形(两两之间有边),那么加上三点点权的乘积
思路:
状态压缩动态规划, dp[st][i][j] 表示状态是st, 前一步在i,现在停在j的最大价值。
cnt[st][i][j] 表示计数。
代码:
#include <cstdio>
#include <cstring>
#include <algorithm> using namespace std; typedef __int64 ll; const int MAXN= ; ll dp[<<][MAXN][MAXN];
ll cnt[<<][MAXN][MAXN]; int G[][];
ll val[];
int n, m; void print() {
for (int i = ; i <= n; i++) {
for (int j = ; j <= n; j++)
printf("%d ", G[i][j]);
puts("");
}
} int main() {
#ifdef Phantom01
freopen("PKU2288.txt", "r", stdin);
#endif // Phantom01 int T;
scanf("%d", &T);
while (T--) {
scanf("%d%d", &n, &m);
memset(dp, , sizeof(dp));
memset(cnt, , sizeof(cnt));
memset(G, , sizeof(G));
for (int i = ; i < n; i++) {
scanf("%I64d", &val[i]);
}
for (int i = ; i < m; i++) {
int u, v;
scanf("%d%d", &u, &v);
G[u-][v-] += ;
G[v-][u-] += ;
}
//print();
if (==n) {
printf("%I64d 1\n", val[]);
continue;
} for (int i = ; i < n; i++)
for (int j = ; j < n; j++) if (G[i][j]){
dp[(<<i)|(<<j)][i][j] = val[i] + val[j] + val[i]*val[j];
cnt[(<<i)|(<<j)][i][j] += G[i][j];
} for (int i = ; i < (<<n)-; i++)
for (int j = ; j < n; j++) if (i&(<<j))
for (int u = ; u < n; u++) if ((i&(<<u)) && (j!=u) && cnt[i][j][u])
for (int v = ; v < n; v++) if (G[u][v] && !(i&(<<v))) {
ll &now = dp[i][j][u];
ll &next = dp[i|(<<v)][u][v];
ll va = val[v]*( + val[u]);
if (G[j][v]) va += val[j]*val[u]*val[v];
if (next < now+va) {
next = now+va;
cnt[i|(<<v)][u][v] = cnt[i][j][u];
} else if (next==now+va)
cnt[i|(<<v)][u][v] += cnt[i][j][u];
} ll ans = , c = ;
for (int i = ; i < n; i++)
for (int j = ; j < n; j++)
if (ans<dp[(<<n)-][i][j]) {
ans = dp[(<<n)-][i][j];
c = cnt[(<<n)-][i][j];
} else if (ans==dp[(<<n)-][i][j])
c += cnt[(<<n)-][i][j]; printf("%I64d %I64d\n", ans, c/);
} return ;
}
PKU2288
P.s.: 开始多开了一维导致MLE,后来发现读错题了 0 0 结果花了一晚上
PKU 2288 Islands and Bridges 状态dp的更多相关文章
- POJ 2288 Islands and Bridges(状压dp)
http://poj.org/problem?id=2288 题意: 有n个岛屿,每个岛屿有一个权值V,一条哈密顿路径C1,C2,...Cn的值为3部分之和: 第1部分,将路径中每个岛屿的权值累加起来 ...
- POJ 2288 Islands and Bridges (状压DP,变形)
题意: 给一个无向图,n个点m条边,每个点有点权,要求找到一条哈密顿路径,使得该路径的f(path)值最大.输出f值,若有多条最大f值的路径,输出路径数量. f值由如下3点累加而来: (1)所有点权之 ...
- poj 2288 Islands and Bridges ——状压DP
题目:http://poj.org/problem?id=2288 状压挺明显的: 一开始写了(记忆化)搜索,但一直T: #include<iostream> #include<cs ...
- poj 2288 Islands and Bridges (状压dp+Tsp问题)
这道题千辛万苦啊! 这道题要涉及到当前点和前面两个点,那就设dp[state][i][j]为当前状态为state,当前点为i,前一个点为j 这个状态表示和之前做炮兵那题很像,就是涉及到三个点时,就多设 ...
- poj 2288 Islands and Bridges——状压dp(哈密尔顿回路)
题目:http://poj.org/problem?id=2288 不知为什么记忆化搜索就是WA得不得了! #include<iostream> #include<cstdio> ...
- POJ 2288 Islands and Bridges(状压DP)题解
题意:n个点,m有向边,w[i]表示i的价值,求价值最大的哈密顿图(只经过所有点一次).价值为:所有点的w之和,加上,每条边的价值 = w[i] * w[j],加上,如果连续的三个点相互连接的价值 = ...
- poj 2288 Islands and Bridges_状态压缩dp_哈密尔顿回路问题
题目链接 题目描述:哈密尔顿路问题.n个点,每一个点有权值,设哈密尔顿路为 C1C2...Cn,Ci的权值为Vi,一条哈密尔顿路的值分为三部分计算: 1.每一个点的权值之和 2.对于图中的每一条CiC ...
- 【以前的空间】poj 2288 Islands and Bridges
一个不错的题解 : http://blog.csdn.net/accry/article/details/6607703 这是一道状态压缩.每个点有一个值,我们最后要求一个最值sum.sum由三部分组 ...
- poj 2288 Islands and Bridges
题意: 给你一个双向连通图,求 获得权值最大 的 哈密顿通路的 权值 和 这个权值对应的数目: 其中权值计算方法是 列如 ABCD 权值是a+b+c+d+ab+bc+cd 如果 A,B,C 和B ...
随机推荐
- 关于PageRank的总结
好久不用CSDN,最近想给带的本科生实验课开个期末习题专题页,发现CSDN的博客忽然要绑定之类.只好弃用回博客园写学习总结了.塞翁失马焉知非福. *************************** ...
- Codeforces 723D. Lakes in Berland
解题思路: 1.dfs所有的水,顺便计数大小并判断是不是湖. 2.如果是湖,将大小和坐标存下来. 3.对湖按大小从小到大排序. 4.dfs前(湖的数量-k)个湖,用*填充这些湖. 代码: #inclu ...
- jQuery学习(二)——使用JQ完成页面定时弹出广告
1.JQuery效果 2.步骤分析: 第一步:引入jQuery相关的文件 第二步:书写页面加载函数 第三步:在页面加载函数中,获取显示广告图片的元素. 第四步:设置定时操作(显示广告图片的函数) 第五 ...
- ASP.NET使用MergeInto做数据同步,同步SQLSERVER不同数据库的相同表结构的数据
public string SynchronousData() { ReturnJson Rejson = new ReturnJson(); //将WebConfig中的数据库连接name中的值写进 ...
- WCF客户端获取服务端异常[自定义异常]
引言 经过不断的摸索,询问/调试,终于学会了关于WCF客户端与服务端之间异常的处理机制,在此来记录自己的成果,用于记录与分享给需要的伙伴们. 首先感谢[.NET技术群]里群主[轩]的大力帮助,如有需要 ...
- [agc004c]and grid
别问我为什么咕了两天 题意: 给出一个$H\times W$的网格图A,仅由'.'和'#'构成,边界上没有'#'且至少有一个'#'.构造两个网格图B和C,大小均为$H\times W$,要求A中为'# ...
- [洛谷P3939]数颜色
题目大意:有n个物品,每个物品有一个颜色.现在有两种操作:1.查询l-r内有多少颜色为c的物品并输出.2.将第x个物品和第x+1个交换.现在让你实现这些操作. 解题思路:首先一共有300000种颜色, ...
- BZOJ 5394 [Ynoi2016]炸脖龙 (线段树+拓展欧拉定理)
题目大意:给你一个序列,需要支持区间修改,以及查询一段区间$a_{i}^{a_{i+1}^{a_{i+2}...}}mod\;p$的值,每次询问的$p$的值不同 对于区间修改,由线段树完成,没什么好说 ...
- 紫书 例题8-16 UVa 1608 (递归)
题意: 判断所给序列是否满足任意连续子序列中至少有一个出现一次的元素. 思路:在整体中找到一个只出现一次的元素, 然后在递归两边.因为两边的序列中有这个数那就满足要求, 所以就看剩下的序列漫步满足要求 ...
- Linux gcc中的LIBRARY_PATH 和 LD_LIBRARY_PATH
1. GNU 上关于LIBRARY_PATH的说明: LIBRARY_PATH The value of LIBRARY_PATH is a colon-separated list of direc ...