题目描述

很久以前,在一个遥远的星系,一个黑暗的帝国靠着它的超级武器统治着整个星系。

某一天,凭着一个偶然的机遇,一支反抗军摧毁了帝国的超级武器,并攻下了星系中几乎所有的星球。这些星球通过特殊的以太隧道互相直接或间接地连接。

但好景不长,很快帝国又重新造出了他的超级武器。凭借这超级武器的力量,帝国开始有计划地摧毁反抗军占领的星球。由于星球的不断被摧毁,两个星球之间的通讯通道也开始不可靠起来。

现在,反抗军首领交给你一个任务:给出原来两个星球之间的以太隧道连通情况以及帝国打击的星球顺序,以尽量快的速度求出每一次打击之后反抗军占据的星球的连通块的个数。(如果两个星球可以通过现存的以太通道直接或间接地连通,则这两个星球在同一个连通块中)。

输入输出格式

输入格式:

输入文件第一行包含两个整数,NN (1 < = N < = 2M1<=N<=2M) 和 MM (1 < = M < = 200,0001<=M<=200,000),分别表示星球的数目和以太隧道的数目。星球用 00 ~ N-1N−1 的整数编号。

接下来的 MM 行,每行包括两个整数 XX, YY,其中( 0 < = X <> Y0<=X<>Y 表示星球 xx 和星球 yy 之间有 “以太” 隧道,可以直接通讯。

接下来的一行为一个整数 kk ,表示将遭受攻击的星球的数目。

接下来的 kk 行,每行有一个整数,按照顺序列出了帝国军的攻击目标。这 kk 个数互不相同,且都在 00 到 n-1n−1的范围内。

输出格式:

第一行是开始时星球的连通块个数。接下来的 KK 行,每行一个整数,表示经过该次打击后现存星球的连通块个数。

输入输出样例

输入样例#1: 复制

8 13
0 1
1 6
6 5
5 0
0 6
1 2
2 3
3 4
4 5
7 1
7 2
7 6
3 6
5
1
6
3
5
7
输出样例#1: 复制

1
1
1
2
3
3
题意: 给n个点(0-n-1) 然后给出m条无向边 每次去掉一个点(该点连接的路自然也断了) 是光笔农场进一步 一开始写了一个最小生成树 最小生成树具有判断联通块的作用
但是只过了两个点 数据2e5 比较大 加上每次都重现最小生成树没有本质上的优化速度 和暴力一样
#include<bits/stdc++.h>
using namespace std;
//input by bxd
#define rep(i,a,b) for(int i=(a);i<=(b);i++)
#define repp(i,a,b) for(int i=(a);i>=(b);i--)
#define RI(n) scanf("%d",&(n))
#define RII(n,m) scanf("%d%d",&n,&m)
#define RIII(n,m,k) scanf("%d%d%d",&n,&m,&k)
#define RS(s) scanf("%s",s);
#define LL long long
#define pb push_back
#define fi first
#define REP(i,N) for(int i=0;i<(N);i++)
#define CLR(A,v) memset(A,v,sizeof A)
///////////////////////////////////
#define inf 0x3f3f3f3f
#define N 200000+5
int f[N];
int vis[N];
int find1(int x)
{
return f[x]==x?x:find1(f[x]);
}
int n,m;
struct node
{
int s,e;
}edge[N]; int kruskal()
{
int x=;
rep(i,,n)
f[i]=i;
rep(i,,m)
{
int a=find1(edge[i].s);
int b=find1(edge[i].e);
if(a==b)continue;
if(vis[ edge[i].s ]||vis[ edge[i].e ])continue;
x++;
f[a]=b;
}
return x;
} int main()
{
RII(n,m);
rep(i,,m)
{
RII(edge[i].s,edge[i].e);
}
printf("%d\n",n-kruskal()+);
int q;
int t=n;
RI(q);
while(q--)
{
int x;
RI(x);
vis[x]=;
t--;
int ans=kruskal();
printf("%d\n",t-ans+);
}
return ;
}
反向并查集  
ans[k+1]等于 一开始 (也就是除了被打破的星球剩下的星球的联通图)
然后i倒叙遍历被打破的点
每次遍历 连通图先加1 因为加入了一个独立的点 然后遍历和这个点有关的所有边 如果另一点是没被打破的 且与该独立点不连通 将其联通 并且ans--;
直到修复到1位置 那么就是正序的原始图了(也就是没有任何一个点被打破的图)
注意实现查找与这个点有关的边链表方法
#include<bits/stdc++.h>
using namespace std;
//input by bxd
#define rep(i,a,b) for(int i=(a);i<=(b);i++)
#define repp(i,a,b) for(int i=(a);i>=(b);i--)
#define RI(n) scanf("%d",&(n))
#define RII(n,m) scanf("%d%d",&n,&m)
#define RIII(n,m,k) scanf("%d%d%d",&n,&m,&k)
#define RS(s) scanf("%s",s);
#define LL long long
#define pb push_back
#define fi first
#define REP(i,N) for(int i=0;i<(N);i++)
#define CLR(A,v) memset(A,v,sizeof A)
///////////////////////////////////
#define inf 0x3f3f3f3f
#define N 400000+5
int f[N];
struct node
{
int s,e,next;
}s[N];
int find1(int x)
{
return f[x]==x?x:f[x]=find1(f[x]);
}
void union1(int a,int b)
{
int x=find1(a);
int y=find1(b);
if(x!=y)f[x]=y;
}
int head[N];
int broken[N];
int node[N];
int ans[N];
int cnt=;
void add(int u,int v)//主要为了更加方便的遍历它的边
{
s[++cnt].s=u; s[cnt].next=head[u];//往回指
head[u]=cnt;
s[cnt].e=v;
}
int main()
{
int n,m;
RII(n,m);
rep(i,,n)
f[i]=i,head[i]=-;//一定要初始化-1 while(m--)
{
int a,b;
RII(a,b);
add(a,b);
add(b,a);
}
int q;
RI(q);
rep(i,,q)
{
RI(node[i]);
broken[node[i]]=;//已经被破坏
}
int sum=n-q;
rep(i,,cnt)//先遍历一遍原始图 也就是除了被打破的星球的图
if(!broken[ s[i].s ]&&!broken[ s[i].e ]&&find1(s[i].s)!=find1(s[i].e))
{
sum--;
union1(s[i].s,s[i].e);
}
ans[q+]=sum;
repp(i,q,)
{
sum++;//每修复一个星球 联通块加一 因为一开始他是独立的
broken[ node[i] ]=;
for(int j=head[node[i]];j!=-;j=s[j].next )
{
if(!broken[s[j].e]&&find1(s[j].e)!=find1(node[i]) )
{
sum--;union1(s[j].e,node[i]);
}
}
ans[i]=sum;
}
rep(i,,q+)
printf("%d\n",ans[i]);
return ; }

P1197 [JSOI2008]星球大战 并查集 反向的更多相关文章

  1. 洛谷P1197 [JSOI2008] 星球大战 [并查集]

    题目传送门 星球大战 题目描述 很久以前,在一个遥远的星系,一个黑暗的帝国靠着它的超级武器统治者整个星系. 某一天,凭着一个偶然的机遇,一支反抗军摧毁了帝国的超级武器,并攻下了星系中几乎所有的星球.这 ...

  2. P1197 [JSOI2008]星球大战[并查集+图论]

    题目来源:洛谷 题目描述 很久以前,在一个遥远的星系,一个黑暗的帝国靠着它的超级武器统治着整个星系. 某一天,凭着一个偶然的机遇,一支反抗军摧毁了帝国的超级武器,并攻下了星系中几乎所有的星球.这些星球 ...

  3. 洛谷 P1197 [JSOI2008]星球大战——并查集

    先上一波题目 https://www.luogu.org/problem/P1197 很明显删除的操作并不好处理 那么我们可以考虑把删边变成加边 只需要一波时间倒流就可以解决拉 储存删边顺序倒过来加边 ...

  4. JSOI2008 星球大战 [并查集]

    题目描述 很久以前,在一个遥远的星系,一个黑暗的帝国靠着它的超级武器统治者整个星系. 某一天,凭着一个偶然的机遇,一支反抗军摧毁了帝国的超级武器,并攻下了星系中几乎所有的星球.这些星球通过特殊的以太隧 ...

  5. [bzoj1015][JSOI2008]星球大战——并查集+离线处理

    题解 给定一张图,支持删点和询问连通块个数 按操作顺序处理的话要在删除点的同时维护图的形态(即图具体的连边情况),这是几乎不可做的 我们发现,这道题可以先读入操作,把没删的点的边先连上,然后再倒序处理 ...

  6. P1197 [JSOI2008]星球大战(并查集判断连通块+正难则反)

    P1197 [JSOI2008]星球大战(并查集判断连通块+正难则反) 并查集本来就是连一对不同父亲的节点就的话连通块就少一个. 题目描述 很久以前,在一个遥远的星系,一个黑暗的帝国靠着它的超级武器统 ...

  7. html5 canvas程序演示--P1197 [JSOI2008]星球大战

    html5 canvas程序演示--P1197 [JSOI2008]星球大战 <!doctype html> <html> <head> <meta char ...

  8. 【反向并查集、联通图】P1197 [JSOI2008]星球大战

    题目描述 很久以前,在一个遥远的星系,一个黑暗的帝国靠着它的超级武器统治着整个星系. 某一天,凭着一个偶然的机遇,一支反抗军摧毁了帝国的超级武器,并攻下了星系中几乎所有的星球.这些星球通过特殊的以太隧 ...

  9. Bzoj1015/洛谷P1197 [JSOI2008]星球大战(并查集)

    题面 Bzoj 洛谷 题解 考虑离线做法,逆序处理,一个一个星球的加入.用并查集维护一下连通性就好了. 具体来说,先将被消灭的星球储存下来,先将没有被消灭的星球用并查集并在一起,这样做可以路径压缩,然 ...

随机推荐

  1. Netty入门(4) - 附带的ChannelHandler和Codec

    使用SSL/TLS创建安全的Netty程序 Java提供了抽象的SslContext和SslEngine,实际上SslContext可以用来获取SslEngine来进行加密和解密.Netty拓展了Ja ...

  2. Java EE之Form的get与post方法

    Form表单中method="post/get'的区别 Form提供了两种数据传输的方式——get和post.虽然它们都是数据的提交方式,但是在实际传输时确有很大的不同,并且可能会对数据产生 ...

  3. dbeaver can't connect HBase1.2 using phoenix driver #1863

    1 第一个问题 Unexpected version format: 10.0.2 Unexpected version format: 10.0.2 Unexpected version forma ...

  4. php 无法正确获取系统当前时间的解决办法

    今天捣鼓一个统计系统时让用户自动录入用户信息,后台使用PHP的date()函数来获取系统时间,发现时间跟当前时间对不上,后来是因为PHP默认的时区是UTC,应该将其时区设置为北京时间. 方法一:修改p ...

  5. 对HUAWEI-ManagedProvisioning的一次不完整分析

    分析思路 关注点1:AndroidManifest.xml是Android应用的入口文件,包含有APP服务的权限.广播和启动位置. 关注点2:涉及到修改系统的函数,setWifiEnabled().I ...

  6. UML和模式应用5:细化阶段(2)--细化阶段制品之领域模型

    1.前言 领域模型是OO分析中最重要和经典的模型.它阐述了领域中的重要概念: 领域模型作为设计某些软件对象的重要来源,也作为案例研究中探讨的几个制品的输入: 领域模型的范围限定于当前迭代开发的用例场景 ...

  7. vs2010补丁

    背景 我都不知道这是干啥的了.想起.net真是一把鼻涕一把泪.搞了这么久.net,也被它坑了好多.有这时间搞搞开源东西多好.看见下面还有tfs,想起当时有个java同事竟然用vss管理java代码,后 ...

  8. C# .NET Winform等程序一运行就闪退 不同环境 换到其他电脑,例如XP之类的解决方法。

    我现在写标题就跟写tag一样,方便大家索引. 有时候经常会把.NET写的程序拿到其他客户机,发现直接闪退,啥也不报错..那就很蛋疼,又不可能去装IDE来检测是吧,网上还有很多说啥看系统日志的,什么图标 ...

  9. Android: SlidingDrawer(滑动式抽屉)

    Android控件之SlidingDrawer(滑动式抽屉)详解与实例 一.简介  SlidingDrawer隐藏屏外的内容,并允许用户通过handle以显示隐藏内容.它可以垂直或水平滑动,它有俩个V ...

  10. Android开源动画库nineoldandroids

    项目官网地址:http://nineoldandroids.com/ 使用这个库的原因是android3.0之后出了新的animation API,但是android3.0以下的不支持 这个库完成了这 ...