zoukankan      html  css  js  c++  java
  • [CF Contest] Web of Lies 题解

    题目描述

    给你一个 (n) 个点 (m) 条边的无向图,要求支持以下几种操作共 (q) 次:

    • 加入一条边 ((u,v))
    • 删除一条边 ((u,v))
    • 查询按照以下步骤对图进行操作后剩下的点的数量:删除所有与其相连的点编号都比其大的点和与该点相连的边,然后再次进行操作,直到删除点的数量为 (0) 为止。(该查询对图的结构不影响)

    数据范围:(1 le n,q le 2cdot 10^5, 0 le m le 2cdot 10^5)

    结论

    对于每一个点,只要有任意相邻的点编号大于它,那么该点一定会在最后一轮前被删除。

    证明

    采用反证法。假如一个有一个相邻点编号大于它,且其存活到了最后一轮。那么其必有一个相邻点小于它。其相邻点若没有编号比其更小的,那么其会在本轮被删除,那本轮不为最后一轮。其相邻点若有编号比其更小的,同样的逻辑也适用于该点。这样我们得到一个无限下降的论证,但编号小于起始点的点数量是有限的,所以产生了矛盾。得证。

    代码实现

    由于正常邻接表的边删除操作不是 (O(1)) 的,所以不能使用邻接表。

    我们可以考虑使用一个叫 alive 的数组来存储 “比编号为 (i) 的点编号大的其邻居的数目”,再使用一个变量 ans 存储每次询问的答案,由于初始所有点都是不连通的,那么 ans 初始化为 (n)

    • 假如一个点加边后有且仅有一个相邻的点编号大于它,答案就减少 (1)
    • 假如一个点删掉与它相邻且唯一的编号大于它的点,答案就增加 (1)

    代码

    #include <iostream>
    #include <cstdio>
    #include <algorithm>
    #include <cstring>
    #include <vector>
    using namespace std;
    
    const int maxn = 2e5 + 5;
    int alive[maxn], n, m;
    
    int main() {
    	cin >> n >> m;
    	int ans = n;
    	for(int i = 1, x, y; i <= m; i ++) {
    		cin >> x >> y;
    		if(x > y) { 
    			alive[y] ++; 
    			if(alive[y] == 1)  ans --; 
    		} else { 
    			alive[x] ++; 
    			if(alive[x] == 1)  ans --; 
    		}
    	}
    	int q;
    	cin >> q;
    	while(q --) {
    		int cmd, x, y;
    		cin >> cmd;
    		if(cmd == 1) {
    			cin >> x >> y;
    			if(x > y) {          // when x is stronger than y
    				alive[y] ++;       // y's dangerous friend ++
    				if(alive[y] == 1) ans --;   // if this is the first dangerous friend, answer --;
    			} else { 
    				alive[x] ++; 
    				if(alive[x] == 1) ans --; 
    			}
    		} else if(cmd == 2) {
    			cin >> x >> y;
    			if(x > y) { 
    				alive[y] --; 
    				if(alive[y] == 0) ans ++; 
    			} else { 
    				alive[x] --; 
    				if(alive[x] == 0) ans ++; 
    			}
    		} else {
    			cout << ans << endl;
    		}
    	}
    }
    
  • 相关阅读:
    LeetCode344
    LeetCode18四数之和扩展N数之和
    LeetCode383赎金信
    2018-2020创业总结
    LeetCode454四数相加
    普通dll项目添加WPF的Window对象
    WPF中RadioButton的数据绑定
    02 C# 文件压缩与解压
    WPF 使用附加属性声明 ICommand
    自定义WPF分页控件
  • 原文地址:https://www.cnblogs.com/Inversentropir-36/p/15094242.html
Copyright © 2011-2022 走看看