CF891C Envy
题面
题解
首先要知道两个性质:
- 对于任意权值,最小生成树上该权值的边数是相同的。
- 对于任意一个最小生成树,当加完所有权值小于一个任意值的边之后,当前图的连通性是一样的。
于是我们按照权值分开处理,对每一种边的权值的每一个询问都处理一遍即可,这个可以写一个到撤销操作的并查集。
于是这道题目就做完了。
代码
#include<cstdio>
#include<cstring>
#include<cctype>
#include<algorithm>
#include<vector>
#define RG register
#define file(x) freopen(#x".in", "r", stdin), freopen(#x".out", "w", stdout)
#define clear(x, y) memset(x, y, sizeof(x))
inline int read()
{
int data = 0, w = 1; char ch = getchar();
while(ch != '-' && (!isdigit(ch))) ch = getchar();
if(ch == '-') w = -1, ch = getchar();
while(isdigit(ch)) data = data * 10 + (ch ^ 48), ch = getchar();
return data * w;
}
const int maxn(5e5 + 10);
struct edge { int x, y, w; } e[maxn];
struct qry { int id, x, y, w; };
inline int cmp(const edge &lhs, const edge &rhs) { return lhs.w < rhs.w; }
std::vector<qry> Q[maxn];
int fa[maxn], size[maxn], ans[maxn], n, m, q, stk[maxn], top;
int find(int x) { return fa[x] == x ? x : find(fa[x]); }
inline int merge(int x, int y)
{
x = find(x), y = find(y);
if(x == y) return 0;
if(size[x] > size[y]) std::swap(x, y);
fa[x] = y, size[y] += size[x], stk[++top] = x;
return 1;
}
int main()
{
n = read(), m = read();
for(RG int i = 1; i <= m; i++)
e[i] = (edge) {read(), read(), read()};
q = read();
for(RG int i = 1, k; i <= q; i++)
{
k = read();
for(RG int j = 1, x; j <= k; j++)
x = read(), Q[e[x].w].push_back((qry) {i, e[x].x, e[x].y, e[x].w});
}
std::sort(e + 1, e + m + 1, cmp);
for(RG int i = 1; i <= n; i++) size[fa[i] = i] = 1;
for(RG int i = 1; i <= q; i++) ans[i] = 1;
for(RG int i = 1; i <= m; i++)
{
int val = e[i].w; top = 0;
for(RG int j = 0; j < (int)Q[val].size(); j++)
{
if(!ans[Q[val][j].id]) continue;
if(j > 0 && Q[val][j].id != Q[val][j - 1].id)
while(top)
{
int x = stk[top--];
size[fa[x]] -= size[x];
fa[x] = x;
}
if(!merge(Q[val][j].x, Q[val][j].y))
ans[Q[val][j].id] = 0;
}
while(e[i].w == val) merge(e[i].x, e[i].y), ++i;
if(e[i].w != val) --i;
}
for(RG int i = 1; i <= q; i++) puts(ans[i] ? "YES" : "NO");
return 0;
}
CF891C Envy的更多相关文章
- CF891C Envy 最小生成树/虚树
正解:最小生成树/虚树 解题报告: 传送门! sd如我就只想到了最暴力的想法,一点儿优化都麻油想到,,,真的菜到爆炸了QAQ 然后就分别港下两个正解QAQ 法一,最小生成树 这个主要是要想到关于最小生 ...
- CF891C Envy(离线/在线+可撤销并查集/并查集/LCT)
前置知识 最小生成树及证明 做法 每个不同权值没影响,仅需判断该次询问每种权值是否在"小于该权值的所有边加完"之后,可以全部加进来 离线:询问的所有边全堆到一起,按权值排序,然后同 ...
- CF891C Envy【最小生成树】
题目链接 我们知道,根据Kruskal的贪心,对于最小生成树,每一种权值的边数是一样的,而且如果将\(\leq x\)的边做最小生成树,合法方案的联通性是一样的.所以我们可以对于所有边分开考虑. 对于 ...
- 题解 [CF891C] Envy
题面 解析 首先根据Kruskal算法, 我们可以知道, 在加入权值为\(w\)的边时, 权值小于\(w\)的边都已经加进树里了(除了连成环的). 所以,我们可以保存一下每条边的端点在加入生成树之前的 ...
- [CF891C] Envy - Kruskal,并查集
给出一个 n 个点 m条边的无向图,每条边有边权,共 Q次询问,每次给出 \(k\)条边,问这些边能否同时在一棵最小生成树上. Solution 所有最小生成树中某权值的边的数量是一定的 加完小于某权 ...
- 【题解】CF891CEnvy
[题解] CF891C Envy 很好玩的一道题.尽管不难,但是调了很久QAQ 考虑克鲁斯卡尔最小生成树的算法,可以发现这些最小树生成的性质: 当生成树所有边的权值都\(\le\)某个$ w$的时刻, ...
- 【CF891C】Envy(最小生成树)
[CF891C]Envy(最小生成树) 题面 Codeforces 洛谷 题解 考虑\(MST\)的构建过程,对于所有权值相同的边一起考虑. 显然最终他们连出来的结果是固定的. 把连边改为把联通块联通 ...
- 【CF891C】Envy 离线+最小生成树
[CF891C]Envy 题意:给你一个图,边有边权,每次询问给你一堆边,问你是否存在一个原图的最小生成树包含给出的所有边.n,m,q<=100000 题解:思路很好的题. 首先有一个非常重要的 ...
- 「CF891C」Envy
传送门 Luogu 解题思路 考虑最小生成树的几个性质: 所有最小生成树中边权相等的边的条数相等 在任意一颗最小生成树中,边权相等的边所联通的点集一定 那么我们考虑把边权相等的边单独拿出来考虑. 每次 ...
随机推荐
- MS SQL backup database的俩个参数
http://msdn.microsoft.com/zh-cn/library/ms186865.aspx 数据传输选项 BUFFERCOUNT = { buffercount | @bufferco ...
- Operating System Error Codes
How To Fix Windows Errors Click here follow the steps to fix Windows and related errors. Instruction ...
- 转:sqlserver 临时表、表变量、CTE的比较
1.临时表 1.1 临时表包括:以#开头的局部临时表,以##开头的全局临时表. 1.2 存储 不管是局部临时表,还是全局临时表,都会放存在tempdb数据库中. 1.3 作用域 局部临时表:对当前连接 ...
- Shell学习---Shell脚本的静态检查工具shellcheck
Shell脚本的静态检查工具shellcheck ubuntu下 apt install shellcheck ,即可安装shellcheck.写完shell脚本,记得用它检查一下,能给你点建议的.要 ...
- 写博的第一天 0x00
作为一个大学生,我觉得自己除了睡觉,打游戏,吃饭更应该做点有意义的事情,作为计算机专业的学生,更应该勤奋点,主动去学习.已经要大三了,我认识到这个暑假我必须学点什么了,为了更好的学习,我决定学语言的同 ...
- SDN期末作业-通过SDN的应用实现负载均衡
负载均衡程序 1.程序链接:https://github.com/424baopu/software/tree/master/LoadBalance 2.场景 topo: 场景描述: 服务器host ...
- 面向对象程序设计_Task7_Summary
Summary of the ... 题目链接:第七次作业 终于还是迎来了这学期的最后一次作业,唠叨话还是放最后说,先说说计算器这玩意儿吧 贯穿了整个学期的计算器,要是让我对自己做个评价,顶多只是还好 ...
- console.time方法与console.timeEnd方法
在Node.js中,当需要统计一段代码的执行时间时,可以使用console.time方法与console.timeEnd方法,其中console.time方法用于标记开始时间,console.time ...
- Concurrent包学习之 BlockingQueue源码学习
上一篇学习了ExecutorService和其它相关类的源码,本篇要学习的BlockingQueue中的源码,as always,先上类图 其实继承(实现)的层次比较简单,我们只要需要先学习一下Blo ...
- The Rock Game
Before the cows head home for rest and recreation, Farmer John wantsthem to get some intellectual st ...