Time Limit: 30 Sec  Memory Limit: 128 MB
Submit: 1171  Solved: 639
[Submit][Status][Discuss]

Description

小铭铭最近进入了某情报部门,该部门正在被如何建立安全的通道连接困扰。

该部门有 n 个情报站,用 1 到 n 的整数编号。给出 m 对情报站 ui;vi 和费用 wi,表示情
报站 ui 和 vi 之间可以花费 wi 单位资源建立通道。
如果一个情报站经过若干个建立好的通道可以到达另外一个情报站,那么这两个情报站就
建立了通道连接。形式化地,若 ui 和 vi 建立了通道,那么它们建立了通道连接;若 ui 和 vi 均
与 ti 建立了通道连接,那么 ui 和 vi 也建立了通道连接。
现在在所有的情报站中,有 p 个重要情报站,其中每个情报站有一个特定的频道。小铭铭
面临的问题是,需要花费最少的资源,使得任意相同频道的情报站之间都建立通道连接。

Input

第一行包含三个整数 n;m;p,表示情报站的数量,可以建立的通道数量和重要情报站的数

量。接下来 m 行,每行包含三个整数 ui;vi;wi,表示可以建立的通道。最后有 p 行,每行包含
两个整数 ci;di,表示重要情报站的频道和情报站的编号。

Output

输出一行一个整数,表示任意相同频道的情报站之间都建立通道连接所花费的最少资源总量。

Sample Input

5 8 4
1 2 3
1 3 2
1 5 1
2 4 2
2 5 1
3 4 3
3 5 1
4 5 1
1 1
1 2
2 3
2 4

Sample Output

4

HINT

选择 (1; 5); (3; 5); (2; 5); (4; 5) 这 4 对情报站连接。

对于 100% 的数据,0 <ci <= p <= 10; 0 <ui;vi;di <= n <= 1000; 0 <= m <= 3000; 0 <= wi <=
20000。
 

Source

斯坦纳森林

设$f[i][sta]$表示$i$号节点,与关键节点的联通性为$sta$时的最小值

假设我们已经求出了$f$

那么我们令$g[sta]$表示,颜色联通性为$sta$时的最小值

$g$比较好求,枚举子集转移就可以

$f$的话,如果学过斯坦纳树也比较好求

按照套路,两种转移方法,一种是枚举子集,一种是SPFA

#include<cstdio>
#include<queue>
#include<cstring>
using namespace std;
const int MAXN = 1e6 + ;
inline int read() {
char c = getchar(); int x = , f = ;
while(c < '' || c > '') {if(c == '-') f = -; c = getchar();}
while(c >= '' && c <= '') {x = x * + c - ''; c = getchar();}
return x * f;
}
int N, M, P;
struct node {
int u, v, w, nxt;
}E[MAXN];
int head[MAXN], num = ;
inline void AddEdge(int x, int y,int z) {
E[num].u = x; E[num].v = y; E[num].w = z;
E[num].nxt = head[x]; head[x] = num++;
}
struct Point {
int color, ID;
}a[MAXN];
int f[][], g[];
int vis[MAXN], sum[MAXN];
queue<int>q;
void SPFA(int now) {
while(q.size() != ) {
int p = q.front(); q.pop(); vis[p] = ;
for(int i = head[p]; i != -; i = E[i].nxt) {
int v = E[i].v;
if(f[v][now] > f[p][now] + E[i].w) {
f[v][now] = f[p][now] + E[i].w;
if(!vis[v]) vis[v] = , q.push(v);
}
}
}
}
int tmp[];
bool check(int sta) {
memset(tmp, , sizeof(tmp));
for(int i = ; i <= ; i++)
if(sta & ( << i - )) tmp[a[i].color]++;
for(int i = ; i <= ; i++)
if(tmp[i] && tmp[i] != sum[i]) return ;
return ;
}
int main() {
#ifdef WIN32
freopen("a.in", "r", stdin);
#endif
memset(head, -, sizeof(head));
N = read(), M = read(), P = read();
for(int i = ; i <= M; i++) {
int x = read(), y = read(), z = read();
AddEdge(x, y, z);AddEdge(y, x, z);
}
memset(f, 0x3f, sizeof(f));
memset(g, 0x3f, sizeof(g));
for(int i = ; i <= P; i++)
a[i].color = read(), a[i].ID = read(), sum[a[i].color]++,f[a[i].ID][ << (i - )] = ;
int limit = ( << P) - ;
for(int sta = ; sta <= limit; sta++) {
for(int i = ; i <= N; i++) {
for(int S = sta; S; S = (S - ) & sta)
f[i][sta] = min(f[i][sta], f[i][S] + f[i][sta - S]);
q.push(i),vis[i] = ;
}
SPFA(sta);
}
for(int sta = ; sta <= limit; sta++)
for(int i = ; i <= N; i++)
g[sta] = min(g[sta], f[i][sta]);
for(int sta = ; sta <= limit; sta++)
if(check(sta))
for(int S = sta; S; S = (S - ) & sta)
if(check(S))
g[sta] = min(g[sta], g[S] + g[sta - S]);
printf("%d", g[( << P) - ]);
return ;
}

BZOJ4006: [JLOI2015]管道连接(斯坦纳树,状压DP)的更多相关文章

  1. 【bzoj4006】[JLOI2015]管道连接 斯坦纳树+状压dp

    题目描述 给出一张 $n$ 个点 $m$ 条边的无向图和 $p$ 个特殊点,每个特殊点有一个颜色.要求选出若干条边,使得颜色相同的特殊点在同一个连通块内.输出最小边权和. 输入 第一行包含三个整数 n ...

  2. bzoj 4006 管道连接 —— 斯坦纳树+状压DP

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=4006 用斯坦纳树求出所有关键点的各种连通情况的代价,把这个作为状压(压的是集合选择情况)的初 ...

  3. BZOJ4006 JLOI2015 管道连接(斯坦纳树生成森林)

    4006: [JLOI2015]管道连接 Time Limit: 30 Sec Memory Limit: 128 MB Description 小铭铭最近进入了某情报部门,该部门正在被如何建立安全的 ...

  4. bzoj 4006 [JLOI2015]管道连接(斯坦纳树+状压DP)

    [题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=4006 [题意] 给定n点m边的图,连接边(u,v)需要花费w,问满足使k个点中同颜色的 ...

  5. BZOJ 4006 Luogu P3264 [JLOI2015]管道连接 (斯坦纳树、状压DP)

    题目链接: (bzoj)https://www.lydsy.com/JudgeOnline/problem.php?id=4006 (luogu)https://www.luogu.org/probl ...

  6. 【BZOJ4774/4006】修路/[JLOI2015]管道连接 斯坦纳树

    [BZOJ4774]修路 Description 村子间的小路年久失修,为了保障村子之间的往来,法珞决定带领大家修路.对于边带权的无向图 G = (V, E),请选择一些边,使得1 <= i & ...

  7. 洛谷P3264 [JLOI2015]管道连接 (斯坦纳树)

    题目链接 题目大意:有一张无向图,每条边有一定的花费,给出一些点集,让你从中选出一些边,用最小的花费将每个点集内的点相互连通,可以使用点集之外的点(如果需要的话). 算是斯坦纳树的入门题吧. 什么是斯 ...

  8. bzoj1402 Ticket to Ride 斯坦纳树 + 状压dp

    给定\(n\)个点,\(m\)条边的带权无向图 选出一些边,使得\(4\)对点之间可达,询问权值最小为多少 \(n \leqslant 30, m \leqslant 1000\) 首先看数据范围,\ ...

  9. BZOJ2595: [Wc2008]游览计划(斯坦纳树,状压DP)

    Time Limit: 10 Sec  Memory Limit: 256 MBSec  Special JudgeSubmit: 2030  Solved: 986[Submit][Status][ ...

随机推荐

  1. 在生产环境中安全执行更新删除SQL脚本的技巧

    今天在生产环境上解决问题,由于广发银行的管理制度是开发公司是不允许确生产环境的,所以我们只能把要更新的语句发给运营中心,由运营中心的投产人员执行,我们则在旁边看着:在他执行的时候发现了一个很有趣的技巧 ...

  2. RNN & LSTM & GRU 的原理与区别

      RNN 循环神经网络,是非线性动态系统,将序列映射到序列,主要参数有五个:[Whv,Whh,Woh,bh,bo,h0][Whv,Whh,Woh,bh,bo,h0],典型的结构图如下: 和普通神经网 ...

  3. 一文详解 Linux 系统常用监控工具(top,htop,iotop,iftop)

      概 述 本文主要记录一下 Linux 系统上一些常用的系统监控工具,非常好用.正所谓磨刀不误砍柴工,花点时间总结一下是值得的! 本文内容脑图如下: top 命令 top 命令我想大家都挺熟悉吧! ...

  4. Two ways to invert a string

    package com.itheima_07; import java.util.Scanner; /* * 字符串反转 * 举例:键盘录入”abc” * 输出结果:”cba” * * 分析: * A ...

  5. linux 网络命令last、lastlog、traceroute、netstat

    last /usr/bin/last语法:last功能:列出目前与过去登入系统的用户信息 reboot 是重启信息 lastlog lastlog -u 502(用户ID) traceroute /b ...

  6. Java中的Number和Math类简单介绍

    Java Number类 一般地,当需要使用数字的时候,我们通常使用内置数据类型,如:byte.int.long.double 等. 实例: int a = 5000; float b = 13.65 ...

  7. Chrome 插件推荐

    我在这里就是抛砖引玉,各位开发者,有更好的插件请不要吝啬,分享出来. 希望世界和平! 翻译类 沙拉查词 目前使用,感觉挺好的,各种词典,还有统计.划词划句都可以翻译出来. JSON 格式转换 JSON ...

  8. 使用ServiceBroker自动激活模拟"秒杀"场景

    1.简介 SQL Server Service Broker 是SQL server 里面比较独特的一个功能.它可帮助开发人员构建异步的松散耦合应用程序 ServiceBroker入门文章:http: ...

  9. 使用eclipse遇到的unable to install breakpoint的问题

    调试一个tomcat工程,设置好断点,启动工程,结果出现了下面的错误: 继续运行,再进入断点之前,还会再度提示,但是最终会命中断点. 使用CGLIB查找关键字,了解到CGLIB是一个AOP的拦截库,想 ...

  10. ASP.NET MVC 5搭建自己的视图基架 (CodeTemplate)

    我们知道,在MVC项目中添加视图时,在添加面板有模板可以选择,这里会有人疑问,这个模板位于哪里?我可以搭建自己的基架吗? 首先回答第二个问题,答案是当然可以 我这里使用的是Visual Studio ...