ZOJ - 3261 逆向并查集
思路:很巧妙的解法。如果按照常规一边读入,一边合并并查集,删边实在没办法做。
首先读入所有的操作,把所有不会被删除的边加入并查集,然后从最后一个操作开始逆向操作,当遇到删边操作,就直接把这条边加入并查集。可以用一个栈保存答案。
注意:当有两个power相同的时候,选择编号更小的。输出之间有空行。
AC代码
#include <cstdio>
#include <cmath>
#include <cctype>
#include <algorithm>
#include <cstring>
#include <utility>
#include <string>
#include <iostream>
#include <map>
#include <set>
#include <vector>
#include <queue>
#include <stack>
using namespace std;
#pragma comment(linker, "/STACK:1024000000,1024000000")
#define eps 1e-10
#define inf 0x3f3f3f3f
#define PI pair<int, int>
typedef long long LL;
const int maxn = 1e4 + 5;
int p[maxn], a[maxn];
struct node{
int x, y;
}b[maxn<<1];
struct oper{
char s[20];
int x, y;
}q[maxn*5];
int find(int x) {
return p[x] == x ? x : p[x] = find(p[x]);
}
void unionset(int x, int y) {
int rx = find(x), ry = find(y);
if(a[rx] == a[ry]) { //当二者的值相同
if(rx < ry) p[ry] = rx;
else p[rx] = ry;
}
else if(a[rx] < a[ry]) {
p[rx] = ry;
}
else p[ry] = rx;
}
int main() {
int n, m, kase = 0;
while(scanf("%d", &n) == 1) {
if(kase++) printf("\n");
for(int i = 0; i <= n; ++i) p[i] = i;
for(int i = 0; i < n; ++i) scanf("%d", &a[i]);
scanf("%d", &m);
int x, y;
for(int i = 1; i <= m; ++i) {
scanf("%d%d", &b[i].x, &b[i].y);
if(b[i].x > b[i].y) swap(b[i].x, b[i].y);
}
int Q;
scanf("%d", &Q);
getchar();
map<PI, int>ha;
char s[30];
for(int i = 1; i <= Q; ++i) {
fgets(s, sizeof(s), stdin);
if(s[0] == 'd') {
sscanf(s, "%s%d%d", &q[i].s, &q[i].x, &q[i].y);
if(q[i].x > q[i].y) swap(q[i].x, q[i].y);
PI pi = make_pair(q[i].x, q[i].y);
ha[pi] = 1;
//printf("%s %d %d\n", q[i].s, q[i].x, q[i].y);
}
else {
sscanf(s, "%s%d", &q[i].s, &q[i].x);
//printf("%s %d\n", q[i].s, q[i].x);
}
}
//建立并查集
for(int i = 1; i <= m; ++i) {
if(!ha.count(make_pair(b[i].x, b[i].y))) {
unionset(b[i].x, b[i].y);
}
}
//逆向
stack<int>ans;
for(int i = Q; i > 0; --i) {
if(q[i].s[0] == 'q') {
int r = find(q[i].x);
if(a[r] <= a[q[i].x]) ans.push(-1);
else ans.push(r);
}
else unionset(q[i].x, q[i].y);
}
while(!ans.empty()) {
printf("%d\n", ans.top());
ans.pop();
}
}
return 0;
}
如有不当之处欢迎指出!
ZOJ - 3261 逆向并查集的更多相关文章
- zoj 3261 逆向并查集+离线处理
题意:给出一些点,每个点有权值,然后有一些边,相连.无向的.然后有一些操作 链接:点我 query a.表示从a出发的能到达的所有点权值最大的点的编号(相同取编号最小,而且权值要比自己大) desto ...
- ZOJ 3261 Connections in Galaxy War(逆向并查集)
参考链接: http://www.cppblog.com/yuan1028/archive/2011/02/13/139990.html http://blog.csdn.net/roney_win/ ...
- HDU - 4496 City 逆向并查集
思路:逆向并查集,逆向加入每一条边即可.在获取联通块数量的时候,直接判断新加入的边是否合并了两个集合,如果合并了说明联通块会减少一个,否则不变. AC代码 #include <cstdio> ...
- HDU_4496_逆向并查集
http://acm.hdu.edu.cn/showproblem.php?pid=4496 逆向并查集,先读取,然后从后向前join每次保存答案即可. #include<iostream> ...
- 逆向并查集 hrbust 1913
#include<iostream> //由于拆除并查集的方法太难或者没有#include<cstdio> //可以先将所有没有拆的桥连接 再逆向操作 断开变成连接 反向输出# ...
- Connections in Galaxy War (逆向并查集)题解
Connections in Galaxy War In order to strengthen the defense ability, many stars in galaxy allied to ...
- ZOJ3261:Connections in Galaxy War(逆向并查集)
Connections in Galaxy War Time Limit: 3 Seconds Memory Limit: 32768 KB 题目链接:http://acm.zju.edu. ...
- BZOJ 1016 星球大战starwar(逆向-并查集)
题目链接:http://61.187.179.132/JudgeOnline/problem.php?id=1015 题意:给出一个图.每次删掉一个点,求删掉之后连通块个数. 思路:正着做不好做,我们 ...
- HDU 4496 D-City(逆向并查集)
http://acm.hdu.edu.cn/showproblem.php?pid=4496 题意: 给出n个顶点m条边的图,每次选择一条边删去,求每次删边后的连通块个数. 思路: 离线处理删边,从后 ...
随机推荐
- python_百文买百鸡问题
百文买百鸡问题 -- 不定方程 -- 公鸡5文钱一只,母鸡3文钱一只,小鸡3只一文钱,用100文钱买100只鸡,如何买? -- 列出方程式 x + y + z = 100 5x + 3y + z/3 ...
- Servlet--ServletInputStream类,ServletOutputStream类
ServletInputStream类 定义 public abstract class ServletInputStream extends InputStream 这个类定义了一个用来读取客户端的 ...
- Java与C/C++的区别
首先应该清楚,Java是由C++发展而来的,它保留了c++的大部分内容,类似于c++,但句法更清晰,规模更小,更易学.它是在对多种程序设计语言进行了深入细致研究的基础上,据弃了其他语言的不足之 ...
- Nagios状态长时间处于Pending的解决方法
1 nagios 守护进程引起的一系列问题 1 影响nagios web页面收集监控信息 致使页面出现时而收集不到服务信息 2 影响pnp查看图形化,出图缓慢 3 影响查看服务状态信息,致使有时候查看 ...
- PHP 第3方评论系统
这段时间,无觅 评论也下线不能使用了. 客户好几个网站使用了.无觅 评论,前面也是用的是多说还是什么,总之也是第3方评论,没想到没过多久,又停止使用了. 没办法,网站还是需要评论系统,一气之下,自己做 ...
- spring实例化bean三种方式
我看了这篇博文<https://www.cnblogs.com/zhanglei93/p/6221546.html>,以及自己实践总结了关于spring实例化bean对象的3种方式. 一. ...
- getHibernateTemplate() VS getSession()
如题所示,对于这个问题,官网文档已给出答案,详见: /** * Obtain a Hibernate Session, either from the current transaction or * ...
- javaweb重定向的两种方式
第一种 import java.io.IOException; import javax.servlet.ServletException; import javax.servlet.http.Htt ...
- 【linux之用户,密码,组管理】
一.用户及密码 用户账户 超级用户:UID=0 root 普通用户:UID!=0 系统用户: 0<UID<500 为了维持系统的某些功能或者实现某些服务 不能完成登录时候的身份验证 普通用 ...
- Java中的双重检查锁(double checked locking)
最初的代码 在最近的项目中,写出了这样的一段代码 private static SomeClass instance; public SomeClass getInstance() { if (nul ...