BZOJ 3624: [Apio2008]免费道路 [生成树 并查集]
题意:
一张图0,1两种边,构造一个恰有k条0边的生成树
优先选择1边构造生成树,看看0边是否小于k
然后保留这些0边,补齐k条,再加1边一定能构成生成树
类似kruskal的证明
#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
const int N=2e4+, M=1e5+;
typedef long long ll;
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, u, v, c, m0, m1, p;
struct meow{int u, v, c;}a[M], b[M], ans[N];
int fa[N];
int find(int x) {return x==fa[x] ? x : fa[x]=find(fa[x]);}
int flag[N];
int main() {
freopen("in","r",stdin);
n=read(); m=read(); k=read();
for(int i=; i<=m; i++) {
u=read(), v=read(), c=read();
if(c==) a[++m1]=(meow){u,v,c};
else b[++m0]=(meow){u,v,c};
} int cnt=;
for(int i=; i<=n; i++) fa[i]=i;
for(int i=; i<=m1; i++) {
u=a[i].u, v=a[i].v;
int x=find(u), y=find(v);
if(x==y) continue;
fa[x]=y;
if(++cnt == n-) break;
}
for(int i=; i<=m0; i++) {
u=b[i].u, v=b[i].v;
int x=find(u), y=find(v);
if(x==y) continue;
fa[x]=y; ans[++p]=b[i]; flag[i]=;
if(++cnt == n-) break;
}
if(p > k || cnt < n-) {puts("no solution"); return ;} for(int i=; i<=n; i++) fa[i]=i;
for(int i=; i<=p; i++) fa[find(ans[i].u)] = find(ans[i].v);
cnt=p;
if(cnt<k) for(int i=; i<=m0; i++) if(!flag[i]){
u=b[i].u, v=b[i].v;
int x=find(u), y=find(v);
if(x==y) continue;
fa[x]=y; ans[++cnt]=b[i];
if(cnt == k) break;
}
for(int i=; i<=m1; i++) {
u=a[i].u, v=a[i].v;
int x=find(u), y=find(v);
if(x==y) continue;
fa[x]=y; ans[++cnt]=a[i];
if(cnt == n-) break;
}
for(int i=; i<=cnt; i++) printf("%d %d %d\n",ans[i].u, ans[i].v, ans[i].c);
}
2017-10-03 今天又写了一下 以前好像有点问题洛谷wa1
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>
#include <cmath>
using namespace std;
const int N = 1e5+, M = 1e5+;
typedef long long ll;
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;
struct edge {int u, v, c;} e[M];
int flag[N], fa[N], ans[N];
int find(int x) {return x == fa[x] ? x : fa[x] = find(fa[x]);}
int main() {
//freopen("in", "r", stdin);
scanf("%d %d %d", &n, &m, &k);
for(int i=; i<=m; i++) e[i].u = read(), e[i].v = read(), e[i].c = read(); for(int i=; i<=n; i++) fa[i] = i;
int num = ;
for(int i=; i<=m; i++) if(e[i].c == ) {
int f1 = find(e[i].u), f2 = find(e[i].v);
if(f1 == f2) continue;
fa[f1] = f2;
if(++num == n-) break;
}
int one = ;
for(int i=; i<=m; i++) if(e[i].c == ) {
int f1 = find(e[i].u), f2 = find(e[i].v);
if(f1 == f2) continue;
fa[f1] = f2;
one++; ans[++ans[]] = i; flag[i] = ;
if(++num == n-) break;
}
if(one > n-k) {puts("no solution"); return ;}
if(num < n-) {puts("no solution"); return ;} for(int i=; i<=n; i++) fa[i] = i;
num = ;
for(int i=; i<=m; i++) if(e[i].c == ) {
int f1 = find(e[i].u), f2 = find(e[i].v);
if(f1 == f2) continue;
fa[f1] = f2;
if(++num == n-) break;
}
int zero = ;
for(int i=; i<=m; i++) if(e[i].c == ) {
int f1 = find(e[i].u), f2 = find(e[i].v);
if(f1 == f2) continue;
fa[f1] = f2;
zero++; ans[++ans[]] = i; flag[i] = ;
if(++num == n-) break;
}
if(zero > k) {puts("no solution"); return ;} for(int i=; i<=n; i++) fa[i] = i;
num = ans[];
for(int i=, t; i<=ans[]; i++) t = ans[i], fa[find(e[t].u)] = find(e[t].v);
if(zero < k) for(int i=; i<=m; i++) if(!flag[i] && e[i].c == ) {
int f1 = find(e[i].u), f2 = find(e[i].v);
if(f1 == f2) continue;
fa[f1] = f2;
ans[++ans[]] = i;
++num;
if(++zero == k) break;
}
if(num < n-) for(int i=; i<=m; i++) if(!flag[i] && e[i].c == ) {
int f1 = find(e[i].u), f2 = find(e[i].v);
if(f1 == f2) continue;
fa[f1] = f2;
ans[++ans[]] = i;
if(++num == n-) break;
} if(zero != k || num != n-) {puts("no solution"); return ;}
for(int i=, t; i<=ans[]; i++) t = ans[i], printf("%d %d %d\n", e[t].u, e[t].v, e[t].c);
}
BZOJ 3624: [Apio2008]免费道路 [生成树 并查集]的更多相关文章
- BZOJ 3624 [Apio2008]免费道路:并查集 + 生成树 + 贪心【恰有k条特殊路径】
题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=3624 题意: 给你一个无向图,n个点,m条边. 有两种边,种类分别用0和1表示. 让你求一 ...
- bzoj 3624: [Apio2008]免费道路 生成树的构造
3624: [Apio2008]免费道路 Time Limit: 2 Sec Memory Limit: 128 MBSec Special JudgeSubmit: 111 Solved: 4 ...
- BZOJ 3624: [Apio2008]免费道路
3624: [Apio2008]免费道路 Time Limit: 2 Sec Memory Limit: 128 MBSec Special JudgeSubmit: 1201 Solved: ...
- bzoj 3624: [Apio2008]免费道路【生成树+贪心】
先把水泥路建生成树,然后加鹅卵石路,这里加的鹅卵石路是一定要用的(连接各个联通块),然后初始化并查集,先把必需的鹅卵石路加进去,然后随便加鹅卵石路直到k条,然后加水泥路即可. 注意判断无解 #incl ...
- Bzoj 3624: [Apio2008]免费道路 (贪心+生成树)
Sample Input 5 7 2 1 3 0 4 5 1 3 2 0 5 3 1 4 3 0 1 2 1 4 2 1 Sample Output 3 2 0 4 3 0 5 3 1 1 2 1 这 ...
- BZOJ.3624.[APIO2008]免费道路(Kruskal)
题目链接 我们发现有些白边是必须加的,有些是多余的. 那么我们先把所有黑边加进去,然后把必须要加的白边找出来. 然后Kruskal,把必须要加的白边先加进去,小于K的话再加能加的白边.然后加黑边. 要 ...
- [APIO2008]免费道路(生成树)
新亚(New Asia)王国有 N 个村庄,由 M 条道路连接.其中一些道路是鹅卵石路,而其它道路是水泥路.保持道路免费运行需要一大笔费用,并且看上去 王国不可能保持所有道路免费.为此亟待制定一个新的 ...
- 3624: [Apio2008]免费道路
Description Input Output Sample Input 5 7 2 1 3 0 4 5 1 3 2 0 5 3 1 4 3 0 1 2 1 4 2 1 Sample Output ...
- [Apio2008]免费道路[Kruscal]
3624: [Apio2008]免费道路 Time Limit: 2 Sec Memory Limit: 128 MBSec Special JudgeSubmit: 1292 Solved: ...
随机推荐
- oracle erp 表结构
BOM模块常用表结构 表名: bom.bom_bill_of_materials 说明: BOM清单父项目 BILL_SEQUENCE_ID NUMBER 清单序号(关键字)ASSEMBLY_ITEM ...
- seaJS 模块加载过程分析
先看一个seajs的官方example, 以下以seajs.use('main')为例, 解析加载mod main的过程 //app.html seajs.use("main") ...
- 【Linux搭建创建FTP服务器】---完美解决 - 费元星
配置大红字文件置顶: vsftp d.conf 4.5KB useradd -d /home/bai_du -s /sbin/nologin bai_du 修改访问权限: usermod ...
- Android开发之漫漫长途 XII——Fragment详解
该文章是一个系列文章,是本人在Android开发的漫漫长途上的一点感想和记录,我会尽量按照先易后难的顺序进行编写该系列.该系列引用了<Android开发艺术探索>以及<深入理解And ...
- 微信小程序:微信登陆(ThinkPHP作后台)
https://www.jianshu.com/p/340b1ba5245e QQ截图20170320170136.png 微信小程序官方给了十分详细的登陆时序图,当然为了安全着想,应该加上签名加 ...
- PHP在线提交留言直接发到邮箱
(2012-08-06 08:57:10) 转载▼ 标签: 杂谈 分类: php email.php 分享: 喜欢 0 赠金笔 阅读┊ 评论 ┊ 收藏 ┊转载 ┊ 喜欢▼ ┊打印┊举报 加载中,请稍候 ...
- ecshop商城_
一.Ecshop简介: ECShop是Comsenz公司推出的一款B2C独立网店系统,适合企业及个人快速构建个性化网上商店.系统是基于PHP语言及MYSQL数据库构架开发的跨平台开源程序. ECSho ...
- RPC架构简单理解
RPC(Remote Promote Call) 一种进程间通信方式.允许像调用本地服务一样调用远程服务. RPC框架的主要目标就是让远程服务调用更简单.透明.RPC框架负责屏蔽底层的传输方式(TCP ...
- Mac下用SSH连接远程Linux或Mac服务器
1.打开Mac终端 2.切换到root登录 输入命令:sudo -i,然后输入本机密码 p.p1 { margin: 0.0px 0.0px 0.0px 0.0px; font: 14.0px &qu ...
- 开源纯C#工控网关+组态软件(八)表达式编译器
一. 引子 监控画面的主要功能之一就是跟踪下位机变量变化,并将这些变化展现为动画.大部分时候,界面上一个图元组件的某个状态,与单一变量Tag绑定,比如电机的运行态,绑定一个MotorRunning ...