Dig The Wells

Time Limit: 6000/2000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Others)

Total Submission(s): 971    Accepted Submission(s): 416

Problem Description
You may all know the famous story “Three monks”. Recently they find some places around their temples can been used to dig some wells. It will help them save a lot of time. But to dig the well or build the road to transport the water
will cost money. They do not want to cost too much money. Now they want you to find a cheapest plan.
 
Input
There are several test cases.

Each test case will starts with three numbers n , m, and p in one line, n stands for the number of monks and m stands for the number of places that can been used, p stands for the number of roads between these places. The places the monks stay is signed from
1 to n then the other m places are signed as n + 1 to n + m. (1 <= n <= 5, 0 <= m <= 1000, 0 <=p <= 5000)

Then n + m numbers followed which stands for the value of digging a well in the ith place.

Then p lines followed. Each line will contains three numbers a, b, and c. means build a road between a and b will cost c.
 
Output
For each case, output the minimum result you can get in one line.
 
Sample Input
3 1 3
1 2 3 4
1 4 2
2 4 2
3 4 4
4 1 4
5 5 5 5 1
1 5 1
2 5 1
3 5 1
4 5 1
 
Sample Output
6
5

题意:有n个和尚。每个和尚一个庙,有m个村庄,p条路。每条路有费用,每个地方打井也须要费用,求最少花多少钱能够使得全部和尚喝上水。

斯坦纳树比較裸的问题。

代码:

/* ***********************************************
Author :rabbit
Created Time :2014/7/17 0:59:57
File Name :13.cpp
************************************************ */
#pragma comment(linker, "/STACK:102400000,102400000")
#include <stdio.h>
#include <iostream>
#include <algorithm>
#include <sstream>
#include <stdlib.h>
#include <string.h>
#include <limits.h>
#include <string>
#include <time.h>
#include <math.h>
#include <queue>
#include <stack>
#include <set>
#include <map>
using namespace std;
#define INF 100000000
#define eps 1e-8
#define pi acosi
typedef long long ll;
int head[1100],tol;
struct Edge{
int next,to,val;
}edge[1001000];
void addedge(int u,int v,int w){
edge[tol].to=v;
edge[tol].next=head[u];
edge[tol].val=w;
head[u]=tol++;
}
int weight[1100],d[1100][1<<5],dp[1100],in[1010][1<<5];
int main()
{
//freopen("data.in","r",stdin);
//freopen("data.out","w",stdout);
int n,m,p;
while(~scanf("%d%d%d",&n,&m,&p)){
memset(head,-1,sizeof(head));tol=0;
for(int i=0;i<n+m;i++)
scanf("%d",&weight[i]);
while(p--){
int u,v,w;
scanf("%d%d%d",&u,&v,&w);
u--;v--;
addedge(u,v,w);
addedge(v,u,w);
}
for(int i=0;i<n+m;i++)
for(int j=0;j<(1<<n);j++)
d[i][j]=INF;
for(int i=0;i<(1<<n);i++)dp[i]=INF;
memset(in,0,sizeof(in));
for(int i=0;i<n;i++)
d[i][1<<i]=weight[i];
for(int i=1;i<(1<<n);i++){
queue<int> Q;
for(int j=0;j<n+m;j++){
for(int k=i&(i-1);k;k=(k-1)&i)
d[j][i]=min(d[j][i],d[j][i-k]+d[j][k]-weight[j]);
if(d[j][i]<INF)Q.push(100000*j+i),in[j][i]=1;
}
while(!Q.empty()){
int v=Q.front()/100000,t=Q.front()%100000;
Q.pop();
in[v][t]=0;
for(int e=head[v];e!=-1;e=edge[e].next){
int s=edge[e].to;
if(d[s][t]>d[v][t]+edge[e].val+weight[s]-weight[v]){
d[s][t]=d[v][t]+edge[e].val+weight[s]-weight[v];
if(!in[s][t]){
in[s][t]=1;
Q.push(100000*s+t);
}
}
}
}
}
for(int i=1;i<(1<<n);i++)
for(int j=0;j<n+m;j++)
dp[i]=min(dp[i],d[j][i]);
for(int i=1;i<(1<<n);i++){
for(int j=i&(i-1);j;j=i&(j-1))
dp[i]=min(dp[i],dp[j]+dp[i-j]);
}
cout<<dp[(1<<n)-1]<<endl;
}
return 0;
}

HDU 4085 Steiner树模板称号的更多相关文章

  1. HDU 4085 Steiner树

    主题链接:pid=4085">http://acm.hdu.edu.cn/showproblem.php? pid=4085 由于这题专门花一晚上学习斯坦纳树.找到比較好的学习资料,链 ...

  2. HDU 1251 Trie树模板题

    1.HDU 1251 统计难题  Trie树模板题,或者map 2.总结:用C++过了,G++就爆内存.. 题意:查找给定前缀的单词数量. #include<iostream> #incl ...

  3. HDU 1166 线段树模板&树状数组模板

    HDU1166 上好的线段树模板&&树状数组模板 自己写的第一棵线段树&第一棵树状数组 莫名的兴奋 线段树: #include <cstdio> using nam ...

  4. HDU - 1251 字典树模板题

    Ignatius最近遇到一个难题,老师交给他很多单词(只有小写字母组成,不会有重复的单词出现),现在老师要他统计出以某个字符串为前缀的单词数量(单词本身也是自己的前缀).  Input输入数据的第一部 ...

  5. HDU(1166),线段树模板,单点更新,区间总和

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1166 第一次做线段树,帆哥的一句话,我记下来了,其实,线段树就是一种处理数据查询和更新的手段. 然后, ...

  6. hdu 2072(字典树模板,set,map均可做)

    地址:http://acm.hdu.edu.cn/showproblem.php?pid=2072 lily的好朋友xiaoou333最近很空,他想了一件没有什么意义的事情,就是统计一篇文章里不同单词 ...

  7. hdu 1754 线段树模板题

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1754 #include <cstdio> #include <cmath> # ...

  8. hdu 1251 字典树模板题 ---多串 查找单词出现次数

    这道题题目里没有给定数据范围 我开了2005  疯狂的WA 然后开了50000, A掉  我以为自己模板理解错  然后一天没吃饭,饿得胃疼还是想着把这题A掉再去吃,谁知竟然是这样的问题,,,呵呵~~~ ...

  9. hdu 2665 划分树模板题(可作为模板)

    Kth number Time Limit: 15000/5000 MS (Java/Others)    Memory Limit: 32768/32768 K (Java/Others)Total ...

随机推荐

  1. javascript---在自由落体实现

    实现一些简单的物业自由落体需要理解: clientHeight:浏览器客户机的整体高度 offsetHeight:物(实例div)高低 offsetTop:从对象client最顶层的距离 简单demo ...

  2. Android规范发展

    一.Android 编码规范 1.java 代码中不出现中文.最多凝视中能够出现中文 2.局部变量命名.静态成员变量命名 仅仅能包括字母,单词首字母出第一个外,都为大写,其它字母都为小写 3.常量命名 ...

  3. 冷市攻略:Listo 教你 25 今天的社会 Swift 语言 - 02 Swift Tour

    import Foundation //******************************************************************************** ...

  4. play framework2.5.

    play framework2 的学习笔记 https://github.com/playframework/playframework https://github.com/playframewor ...

  5. spring mvc综合easyui点击上面菜单栏中的菜单项问题

    采用easyui的tree报错发生的背景后,会弹出一个窗口,有一个问题是,当你点击顶部   解决方案,如下面(运用easyui1.36): /home/cyz/workspace/hb_manager ...

  6. Spring的文件上传

    Spring在发现包括multipart的请求后,会使用MultipartResolver的实现bean处理文件上传操作,现有採用Servlet3的 org.springframework.web.m ...

  7. YT新人之巅峰大决战04

    Problem Description Eddy's interest is very extensive, recently he is interested in prime number. Ed ...

  8. Chrome 控制台不完全指南(转)

    Chrome的开发者工具已经强大到没朋友的地步了,特别是其功能丰富界面友好的console,使用得当可以有如下功效: 更高「逼格」更快「开发调试」更强「进阶级的Frontender」 Bug无处遁形「 ...

  9. iphone内容开发技术学习

    一.iOS基础 1 开发环境搭建以及IOS组件.框架的概要介绍. 2 mac操作系统与iOS操作系统 3 xcode IDE开发环境的初始 二.C语言基础 1数据类型.表达式与控制流程语句 2数组.函 ...

  10. paip.jdk1.4 1.5(5.0) 1.6(6.0) 7.0 8.0特点比较与不同

    paip.jdk1.4 1.5(5.0)  1.6(6.0) 7.0   8.0特点比较与不同 作者Attilax ,  EMAIL:1466519819@qq.com 来源:attilax的专栏 地 ...