NOIP2017宝藏 [搜索/状压dp]
NOIP2017 宝藏
题目描述
参与考古挖掘的小明得到了一份藏宝图,藏宝图上标出了 n 个深埋在地下的宝藏屋, 也给出了这 n 个宝藏屋之间可供开发的 m 条道路和它们的长度。
小明决心亲自前往挖掘所有宝藏屋中的宝藏。但是,每个宝藏屋距离地面都很远, 也就是说,从地面打通一条到某个宝藏屋的道路是很困难的,而开发宝藏屋之间的道路 则相对容易很多。
小明的决心感动了考古挖掘的赞助商,赞助商决定免费赞助他打通一条从地面到某 个宝藏屋的通道,通往哪个宝藏屋则由小明来决定。
在此基础上,小明还需要考虑如何开凿宝藏屋之间的道路。已经开凿出的道路可以 任意通行不消耗代价。每开凿出一条新道路,小明就会与考古队一起挖掘出由该条道路 所能到达的宝藏屋的宝藏。另外,小明不想开发无用道路,即两个已经被挖掘过的宝藏 屋之间的道路无需再开发。
新开发一条道路的代价是:
\]
L代表这条道路的长度,K代表从赞助商帮你打通的宝藏屋到这条道路起点的宝藏屋所经过的 宝藏屋的数量(包括赞助商帮你打通的宝藏屋和这条道路起点的宝藏屋.
请你编写程序为小明选定由赞助商打通的宝藏屋和之后开凿的道路,使得工程总代 价最小,并输出这个最小值。
输入输出格式
输入格式:
第一行两个用空格分离的正整数 n 和 m,代表宝藏屋的个数和道路数。
接下来 m 行,每行三个用空格分离的正整数,分别是由一条道路连接的两个宝藏 屋的编号(编号为 1~n),和这条道路的长度 v。
输出格式:
输出共一行,一个正整数,表示最小的总代价.
输入输出样例
输入样例#1:
4 5
1 2 1
1 3 3
1 4 1
2 3 4
3 4 1
输出样例#1:
4
输入样例#2:
4 5
1 2 1
1 3 3
1 4 1
2 3 4
3 4 2
输出样例#2:
5
解题思路:
看到题目数据的第一反应,这是一道状压dp题,可是这和传统的状压不一样,思前想后也想不出状态转移方程,怎么办?
先考虑一波部分分,20%数据很好打,数据保证是一棵树,且v值相同,那就直接搜索乱搞,40%数据和20%差不多,spfa和floyed都可以过,这样40分就轻松拿到,在考场上这样的分数还算可观
因为n非常小,我们可以类比状压的思路进行搜索.看到数据范围,点很少,而边很多,那么就必定有许多重边,所以在搜索之前我们要先处理出两点之间的最短距离(用邻接矩阵),然后就是枚举每个点进行搜索,用一个数组f来表示走过的点的集合,然后在搜索中用已经到达的点去更新还没到达的点,更新方法和40分做法差不多
#include<bits/stdc++.h>
#define il inline
#define rg register
#define lol long long
#define Min(a,b) (a)<(b)?(a):(b)
#define Max(a,b) (a)>(b)?(a):(b)
using namespace std;
const int N=13,M=1010;
const int inf=2e9;
void in(int &ans) {
ans=0; int f=1; char i=getchar();
while(i<'0' || i>'9') {if(i=='-') f=-1; i=getchar();}
while(i>='0' && i<='9') ans=(ans<<1)+(ans<<3)+i-'0', i=getchar();
ans*=f;
}
int n,m,cur,ans=inf;
int dp[1<<12],num[N],line[N][N];
void dfs(int sta) {
for(rg int u=1;u<=n;u++) {
if(!((1<<u-1)&sta)) continue;
for(rg int v=1;v<=n;v++) {
if((1<<v-1)&sta) continue;
if(line[u][v]==line[0][0]) continue;
if(dp[sta|(1<<v-1)]>dp[sta]+line[u][v]*num[u]) {
dp[sta|(1<<v-1)]=dp[sta]+line[u][v]*num[u];
int c=num[v];
num[v]=num[u]+1,dfs(sta|(1<<v-1)),num[v]=c;
}
}
}
}
int main()
{
in(n),in(m); memset(line,0x3f,sizeof(line));
for(rg int i=1,a,b,c;i<=m;i++) {
in(a),in(b),in(c);
line[a][b]=line[b][a]=Min(line[a][b],c);
}
for(rg int i=1;i<=n;i++) {
memset(dp,0x3f,sizeof(dp));
memset(num,0,sizeof(num));
num[i]=1; dp[1<<i-1]=0;
dfs(1<<i-1); ans=Min(ans,dp[(1<<n)-1]);
}
printf("%d\n",ans);
return 0;
}
NOIP2017宝藏 [搜索/状压dp]的更多相关文章
- Luogu3959 NOIP2017宝藏(状压dp)
按层dp,f[i][j]表示已扩展i子集的节点当前在第j层的最小代价,预处理点集间距离即可. #include<iostream> #include<cstdio> #incl ...
- 洛谷P3959 宝藏(NOIP2017)(状压DP,子集DP)
洛谷题目传送门 Dalao的题解多数是什么模拟退火.DFS剪枝.\(O(3^nn^2)\)的状压DP之类.蒟蒻尝试着把状压改进了一下使复杂度降到\(O(3^nn)\). 考虑到每条边的贡献跟它所在的层 ...
- 【NOIP2017】宝藏(状压DP)
题意: 思路:n<=12,考虑状压DP 生成树中深度相同的点可以一次性转移完毕 设dp[sta,i]为已转移完sta状态的点,当前深度为i的最小花费 dp[sta or v,i+1]=min(d ...
- 【题解】洛谷P3959 [NOIP2017TG] 宝藏(状压DP+DFS)
洛谷P3959:https://www.luogu.org/problemnew/show/P3959 前言 NOIP2017时还很弱(现在也很弱 看出来是DP 但是并不会状压DP 现在看来思路并不复 ...
- 洛谷P3959 宝藏(状压dp)
传送门 为什么感觉状压dp都好玄学……FlashHu大佬太强啦…… 设$f_{i,j}$表示当前选的点集为$i$,下一次要加入的点集为$j$时,新加入的点和原有的点之间的最小边权.具体的转移可以枚举$ ...
- 洛谷 3959 宝藏——枚举+状压dp
题目:https://www.luogu.org/problemnew/show/P3959 原来写了个不枚举起点的状压dp. #include<iostream> #include< ...
- 【luoguP3959 宝藏】-状压DP
题目描述: 参与考古挖掘的小明得到了一份藏宝图,藏宝图上标出了 n 个深埋在地下的宝藏屋, 也给出了这 n 个宝藏屋之间可供开发的m 条道路和它们的长度. 小明决心亲自前往挖掘所有宝藏屋中的宝藏.但是 ...
- URAL 1152. False Mirrors (记忆化搜索 状压DP)
题目链接 题意 : 每一颗子弹破坏了三个邻近的阳台.(第N个阳台是与第1个相邻)射击后后的生存的怪物都对主角造成伤害- 如此,直到所有的怪物被消灭,求怎样射击才能受到最少伤害. 思路 : 状压,数据不 ...
- NOIP2017 Day2 T2 宝藏(状压DP)
$O(n*3^n)$好难想...还有好多没见过的操作 令$f[i][j]$表示最深深度为i,点的状态为j的最小代价,每次枚举状态$S$后,计算$S$的补集里的每个点与S里的点的最小连边代价,再$O(3 ...
随机推荐
- C语言实现简易扫雷
首先,写代码之前要将整体思路写出来: 扫雷游戏:1.需要两个二维数组,一个用来展示,一个用来放雷; 2.整体骨架在代码中都有注释说明; 3.游戏难度比较简单,适合初学者观看,如果有大佬看明白,可以指点 ...
- C语言的结构体,枚举类型在程序中的作用
http://www.xue63.com/xueask-1221-12212854.html 结构和枚举类型从程序实现的角度来说,是用更接近自然语言的方式来表达数据.比如说实现2维空间的点,你可以使用 ...
- 嵌入式框架Zorb Framework搭建三:列表的实现
我是卓波,我是一名嵌入式工程师,我万万没想到我会在这里跟大家吹牛皮. 嵌入式框架Zorb Framework搭建过程 嵌入式框架Zorb Framework搭建一:嵌入式环境搭建.调试输出和建立时间系 ...
- 002---Python基本数据类型--字符串
字符串 .caret, .dropup > .btn > .caret { border-top-color: #000 !important; } .label { border: 1p ...
- python中矢量化字符串方法
- Git 查看远程分支、本地分支、删除本地分支及远程分支
1. 删除本地分支: git branch -d branchName 2. 删除远程分支: // 方法一:将删除的本地分支推到远程(要删除的远程分支在本地有映射) git push origin : ...
- php简易实现计划任务
index.php <?php function ceshi(){ $wan = file_get_contents('./wangt_index.txt',true); $jifen = $w ...
- 对mysqlbinlog日志进行操作的总结包括 启用,过期自动删除
操作命令: show binlog events in 'binlog.000016' limit 10; reset master 删除所有的二进制日志 flush logs 产生一个新的binl ...
- (原)MongoDB在系统中的使用
序)Nosql并不是要取代原有的数据产品,而是为不同的应用场景提供更多的选择. 一)结构类型 传统数据库的领域在于结构化文档,对于非结构化文档和半结构化文档,它能处理,但是有一定的缺陷,那么什么又是结 ...
- 「日常训练」 Soldier and Cards (CFR304D2C)
题意 (Codeforces 546C) 按照指定的规则打牌,问谁胜或无穷尽. 分析 又是一条模拟,用set+queue(这里手写了)处理即可.注意到两种局势"1 234"和&qu ...