题意

题目链接

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 ;
}

最新文章

  1. strcpy 库函数 拷贝函数
  2. c++模板使用出错情况error LNK2019: unresolved external symbol &quot;public: float __thiscall Compare&lt;float&gt;::min(void)&quot; (?min@?$Compare@M@@QAEMXZ) referenced in function _main
  3. [NOIP2012] 提高组 洛谷P1081 开车旅行
  4. mysql的Replication机制
  5. Unity 视频播放杂谈
  6. 临时表VS表变量--因地制宜,合理使用
  7. bat 结束进程
  8. tomcat下bin文件夹下shell文件分析
  9. Link Management Protocol (LMP)
  10. WF学习笔记(一)
  11. 同步异步GET和POST请求
  12. back_inserter的用法
  13. 从 Qt 的 delete 说开来
  14. 应用程序启动后修改自身EXE文件或自删除EXE文件(附VC++6.0源码)
  15. protobuf java基础
  16. ArcGIS Portal与Adapter安装问题
  17. js便签笔记(10) - 分享:json.js源码解读笔记
  18. 《转载》WIN10 64位系统 32位Python2.7 PIL安装
  19. A glance at C# vNext
  20. overlay实现容器跨主机通信

热门文章

  1. SM4算法的c++实现
  2. mongodb 操作数据库
  3. sell01 环境搭建、编写持久层并进行测试
  4. hdu1067
  5. hdu1064
  6. C# 中介者模式
  7. 关于nginx的使用感想
  8. [CentOS7] firewalld重启失败 Failed to start firewalld - dynamic firewall daemon.
  9. wxpython实现文件拖拽
  10. HTML 代码格式