Buy or Build(UVa1151)
如果枚举每个套餐,并每次都求最小生成树,总时间复杂度会很高,因而需要先求一次原图的最小生成树,则枚举套餐之后需要考虑的边大大减少了。
具体见代码:
#include<cstdio>
#include<cmath>
#include<cstring>
#include<vector>
#include<algorithm>
using namespace std; const int maxn = + ;
const int maxq = ;
int n;
int x[maxn], y[maxn], cost[maxq];
vector<int> subn[maxq]; int pa[maxn];
int findset(int x) { return pa[x] != x ? pa[x] = findset(pa[x]) : x; } struct Edge {
int u, v, d;
Edge(int u, int v, int d):u(u),v(v),d(d) {}
bool operator < (const Edge& rhs) const {
return d < rhs.d;
}
}; // initialize pa and sort e before calling this method
// cnt is the current number of components
int MST(int cnt, const vector<Edge>& e, vector<Edge>& used) {
if(cnt == ) return ;
int m = e.size();
int ans = ;
used.clear();
for(int i = ; i < m; i++) {
int u = findset(e[i].u), v = findset(e[i].v);
int d = e[i].d;
if(u != v) {
pa[u] = v;
ans += d;
used.push_back(e[i]);
if(--cnt == ) break;
}
}
return ans;
} int main() {
int T, q;
scanf("%d", &T);
while(T--) {
scanf("%d%d", &n, &q);
for(int i = ; i < q; i++) {
int cnt;
scanf("%d%d", &cnt, &cost[i]);
subn[i].clear();
while(cnt--) {
int u;
scanf("%d", &u);
subn[i].push_back(u-);
}
}
for(int i = ; i < n; i++) scanf("%d%d", &x[i], &y[i]); vector<Edge> e, need;
for(int i = ; i < n; i++)
for(int j = i+; j < n; j++) {///建图
int c = (x[i]-x[j])*(x[i]-x[j]) + (y[i]-y[j])*(y[i]-y[j]);
e.push_back(Edge(i, j, c));
} for(int i = ; i < n; i++) pa[i] = i;
sort(e.begin(), e.end());///排序 int ans = MST(n, e, need);///第一次求原图
for(int mask = ; mask < (<<q); mask++) {
/// union cities in the same sub-network
for(int i = ; i < n; i++) pa[i] = i;
int cnt = n, c = ;
for(int i = ; i < q; i++) if(mask & (<<i)) {
c += cost[i];
for(int j = ; j < subn[i].size(); j++) {
int u = findset(subn[i][j]), v = findset(subn[i][]);
if(u != v) { pa[u] = v; cnt--; }
}
}
vector<Edge> dummy;
ans = min(ans, c + MST(cnt, need, dummy));///cnt表示剩余的城市数量,比较每次添加套餐和不添加套餐的花费
}
printf("%d\n", ans);
if(T) printf("\n");
}
return ;
}
Buy or Build(UVa1151)的更多相关文章
- POJ(2784)Buy or Build
Buy or Build Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 1369 Accepted: 542 Descr ...
- Buy or Build (poj 2784 最小生成树)
Buy or Build Time Limit: 2000MS Memory Limit: 65536K Total Submissions: 1348 Accepted: 533 Descr ...
- UVa1151 Buy or Build
填坑(p.358) 以前天真的以为用prim把n-1条边求出来就可以 现在看来是我想多了 #include<cstdio> #include<cstring> #include ...
- 【最小生成树+子集枚举】Uva1151 Buy or Build
Description 平面上有n个点(1<=N<=1000),你的任务是让所有n个点连通,为此,你可以新建一些边,费用等于两个端点的欧几里得距离的平方. 另外还有q(0<=q< ...
- 洛谷 题解 UVA1151 【买还是建 Buy or Build】
[题意] 平面上有\(n(n<=1000)\)个点,你的任务是让所有n个点联通.为此,你可以新建一些边,费用等于两个端点的欧几里得距离平方.另外还有\(q(q<=8)\)个套餐可以购买,如 ...
- UVA 1151 Buy or Build MST(最小生成树)
题意: 在平面上有n个点,要让所有n个点都连通,所以你要构造一些边来连通他们,连通的费用等于两个端点的欧几里得距离的平方.另外还有q个套餐,可以购买,如果你购买了第i个套餐,该套餐中的所有结点将变得相 ...
- UVA 1151 Buy or Build (最小生成树)
先求出原图的最小生成树,然后枚举买哪些套餐,把一个套餐内的点相互之间边权为0,直接用并查集缩点.正确性是基于一个贪心, 在做Kruskal算法是,对于没有进入最小生成树的边,排序在它前面的边不会减少. ...
- UVA 1151 Buy or Build (MST最小生成树,kruscal,变形)
题意: 要使n个点之间能够互通,要使两点直接互通需要耗费它们之间的欧几里得距离的平方大小的花费,这说明每两个点都可以使其互通.接着有q个套餐可以选,一旦选了这些套餐,他们所包含的点自动就连起来了,所需 ...
- UVa 1151 (枚举 + MST) Buy or Build
题意: 平面上有n个点,现在要把它们全部连通起来.现在有q个套餐,如果购买了第i个套餐,则这个套餐中的点全部连通起来.也可以自己单独地建一条边,费用为两点欧几里得距离的平方.求使所有点连通的最小费用. ...
随机推荐
- explode() 字符串分割函数
说明 本函数返回由字符串组成的数组,其中的每个元素都是由 separator 作为边界点分割出来的子字符串. separator 参数不能是空字符串.如果 separator 为空字符串(" ...
- css制作倒三角
布局div,并命名为id="dropdown",在style使用border属性对div进行控制 #dropdown{ width:0px; height:0px; border- ...
- PHP运算符知识
1.三目运算符: $a =1; echo $a>0 ? '大于0':$a==0 ? '等于0':'小于0'; 貌似应该输出:大于0 其实: 然而,上面语句的实际输出是't',因为三元运算符是从左 ...
- 第四周博客之一---Linux的基本命令(前5个)
一.Linux的系统结构 "/"根目录部分有以下子目录: 1./bin:系统启动时需要的执行文件(二进制),这些文件可以被普通用户使用. 2./boot:用于自举加载程序(LILO ...
- 2、CentOS下编译安装Python2.7.6(转)
CentOS系统下面Python在升级到2.7.6的时候,没有找到安装包直接安装,只能通过源代码编译的方式来安装Python 2.7.6版本.这篇是编译和安装Python2.7.6的过程记录. Cen ...
- python 全栈开发笔记 2
函数 函数式:将某功能代码封装到函数中,日后便无需重复编写,仅调用函数即可 面向对象:对函数进行分类和封装,让开发“更快更好更强...” 函数式编程最重要的是增强代码的重用性和可读性 def xx() ...
- Visual Studio 2017 离线安装包
vs_community.exe --layout D:vs2017offline-en --add Microsoft.VisualStudio.Workload.ManagedDesktop -- ...
- Python中集合set()的使用及处理
在Python中集合(set)与字典(dict)比较相似,都具有无序以及元素不能重复的特点 1.创建set 创建set需要一个list或者tuple或者dict作为输入集合 重复的元素在set中会被自 ...
- JavaWeb基础-Jsp的请求与响应
JSP请求和相应 HTTP头信息 当浏览器请求一个网页时,它会向网络服务器发送一系列不能被直接读取的信息,因为这些信息是作为HTTP信息头的一部分来传送的. HttpServletRequest类 r ...
- 二、redis持久化
一.redis持久化 1 RDB持久化(定redis的数据定时dump到磁盘上的RDB持久化)RDB持久化是指在指定的时间间隔内将内存中的数据集快照写入磁盘,实际操作过程是fork一个子进程,先将数据 ...