BZOJ3624: [Apio2008]免费道路(最小生成树)
题意
Sol
首先答案一定是一棵树
这棵树上有一些0边是必须要选的,我们先把他们找出来,如果数量$\geqslant k$显然无解
再考虑继续往里面加0的边,判断能否加到k条即可
具体做法是:
先让1在前做生成树,其中加入的0边是必须要选的
再让0边在前做生成树,这时候我们不必考虑最后能否生成一棵树,只需要考虑能否加入k条即可
我的思路:首先必选的0边是一定要统计出来的,然后一次性把剩下的所有0边都加进去,显然其中会有很多没有用,如果加入的边数量$<k$则无解,
否则考虑删除一些0边,LCT维护形成环后每个环上0边的数量,如果环上0的数量$>0$则减一,把该1边加入,否则不加入。如果总的0边数量为k,
直接不断加剩下的边,最后判断能否形成一棵树,否则0边的数量>k,证明无解。
应该是对的吧,不过打死我也不会去写的。。。。。
#include<cstdio>
#include<algorithm>
#define LL long long
using namespace std;
const int MAXN = * 1e5 + , INF = 1e9 +;
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, K, num, mt, fa[MAXN];
struct Edge {
int u, v, w, f;
bool operator < (const Edge &rhs) const {return w > rhs.w;}
}E[MAXN];
void AddEdge(int x, int y, int z) {E[++num] = (Edge) {x, y, z};}
int comp(const Edge &a, const Edge &b) {return a.w < b.w;}
int find(int x) {return fa[x] == x ? fa[x] : (fa[x] = find(fa[x]));}
int calc() {
int ans = ;
for(int i = ; i <= num; i++) if(E[i].f) ans++;
return ans;
}
int Kruskal(int opt) {
if(opt == ) sort(E + , E + num + );
else sort(E + , E + num + , comp);
for(int i = ; i <= N; i++) fa[i] = i;
int cnt = ;
if(opt == )
for(int i = ; i <= num; i++)
if(E[i].f) fa[find(E[i].u)] = find(E[i].v), cnt++;
for(int i = ; i <= num; i++) {
int x = E[i].u, y = E[i].v, w = E[i].w;
int fx = find(x), fy = find(y);
if(fx == fy) continue;
if(opt == ) {
if(w == ) E[i].f = ;
if((++cnt) == N - ) return calc();
} else if(opt == ) {
cnt++; E[i].f = ;
if(cnt == K) return ;
} else if(opt == ) {
if(w == && (!E[i].f)) continue;
if((++cnt <= N - )) printf("%d %d %d\n", x, y, w);
}
fa[fx] = fy;
}
return ;
}
int main() {
N = read(); M = read(); K = read();
for(int i = ; i <= M; i++) {
int x = read(), y = read(), z = read();
AddEdge(x, y, z); //AddEdge(y, x, z);
}
if(Kruskal() > K) {puts("no solution"); return ;}
if(!Kruskal()) {puts("no soltion"); return ;}
Kruskal();
return ;
}
BZOJ3624: [Apio2008]免费道路(最小生成树)的更多相关文章
- [BZOJ3624][Apio2008]免费道路
[BZOJ3624][Apio2008]免费道路 试题描述 输入 输出 输入示例 输出示例 数据规模及约定 见“输入”. 题解 第一步,先尽量加入 c = 1 的边,若未形成一个连通块,则得到必须加入 ...
- [Apio2008]免费道路[Kruscal]
3624: [Apio2008]免费道路 Time Limit: 2 Sec Memory Limit: 128 MBSec Special JudgeSubmit: 1292 Solved: ...
- Kruskal算法及其类似原理的应用——【BZOJ 3654】tree&&【BZOJ 3624】[Apio2008]免费道路
首先让我们来介绍Krukal算法,他是一种用来求解最小生成树问题的算法,首先把边按边权排序,然后贪心得从最小开始往大里取,只要那个边的两端点暂时还没有在一个联通块里,我们就把他相连,只要这个图里存在最 ...
- bzoj 3624: [Apio2008]免费道路 生成树的构造
3624: [Apio2008]免费道路 Time Limit: 2 Sec Memory Limit: 128 MBSec Special JudgeSubmit: 111 Solved: 4 ...
- 题解 Luogu P3623 [APIO2008]免费道路
[APIO2008]免费道路 题目描述 新亚(New Asia)王国有 N 个村庄,由 M 条道路连接.其中一些道路是鹅卵石路,而其它道路是水泥路.保持道路免费运行需要一大笔费用,并且看上去 王国不可 ...
- BZOJ 3624: [Apio2008]免费道路
3624: [Apio2008]免费道路 Time Limit: 2 Sec Memory Limit: 128 MBSec Special JudgeSubmit: 1201 Solved: ...
- P3623 [APIO2008]免费道路
3624: [Apio2008]免费道路 Time Limit: 2 Sec Memory Limit: 128 MBSec Special Judge Submit: 2143 Solved: 88 ...
- [APIO2008]免费道路
[APIO2008]免费道路 BZOJ luogu 先把必须连的鹅卵石路连上,大于k条no solution 什么样的鹅卵石路(u,v)必须连?所有水泥路都连上仍然不能使u,v连通的必须连 补全到k条 ...
- [APIO2008]免费道路(生成树)
新亚(New Asia)王国有 N 个村庄,由 M 条道路连接.其中一些道路是鹅卵石路,而其它道路是水泥路.保持道路免费运行需要一大笔费用,并且看上去 王国不可能保持所有道路免费.为此亟待制定一个新的 ...
随机推荐
- day18-事务与连接池 4.事务特性
- mongodb操作数据集合
1.创建数据集: a.创建不设置参数的默认数据集(默认数据集自带一个流水id,_id) db.createCollection("mycol") //创建默认集合 b.创建指定参数 ...
- 1、perl学习
1.字符串函数 print chomp chop length uc lc index ord #转符号为ASCII的数字 chr #转数字为ASCII的字母 substr($string,offse ...
- p1098 逆序对
传送门 题目 输入格式: 第一行,一个数n,表示序列中有n个数. 第二行n个数,表示给定的序列. 输出格式: 给定序列中逆序对的数目. 数据范围: 对于50%的数据,n≤2500 对于100%的数据, ...
- Python版的数据库查询构造器、ORM及动态迁移数据表。
Orator Orator提供一个简单和方便的数据库数据处理库. 它的灵感来源于PHP的Laravel框架,借助其思想实现了python版的查询构造器和ORM. 这是完整的文档:http://orat ...
- php小块代码
//页面本身网址 "http://".$_SERVER["HTTP_HOST"].preg_replace("/[^\/]+$/",&quo ...
- Libvirt代码架构
Libvirt介绍 参考资料 Libvirt学习 通过virsh了解libvirt api的调用方式 通过virHypervisorDriver了解libvirt api的实现 virsh代码阅读 通 ...
- BKMigration
PAAS 1. 停止服务 ./bkcec stop paas 2. 修改install.config 3. 删除中控机 /data/install/.bk_install.step 和原p ...
- poj3694(lca + tarjan求桥模板)
题目链接: http://poj.org/problem?id=3694 题意: 给出一个 n 个节点 m 条边的图, 然后有 q 组形如 x, y 的询问, 在前面的基础上连接边 x, y, 输出当 ...
- 51nod1305(简单逻辑)
题目链接:https://www.51nod.com/onlineJudge/questionCode.html#!problemId=1305 题意:中文题诶- 思路:1e5的数据直接暴力肯定是不行 ...