gjh303987897 @ 2021-11-15 20:02:47
#include<iostream>
#include<cstdio>
#include<algorithm>
#include<cstring>
#include<cmath>
#include<queue>
#define maxn 500005
using namespace std;
int n,m,k,ans[maxn],vis[maxn],fa[maxn],x[maxn],y[maxn],bui[maxn];
int read(){
int x=0,f=1; char ch=getchar();
while(ch<'0'||ch>'9'){
if(ch=='-') f=-1;
ch=getchar();
}
while(ch<='9'&&ch>='0'){
x=(x<<3)+(x<<1)+(ch^48);
ch=getchar();
}
return x*f;
}
struct data{
int next,to;
}t[maxn*2+1];
int head[maxn],js;
inline void add(int u,int v){
t[++js].next=head[u];
head[u]=js;
t[js].to=v;
}
int find(int r){
if(fa[r]!=r) fa[r]=find(fa[r]);
return fa[r];
}
void un(int r1,int r2){
r1=find(r1); r2=find(r2);
if(r1!=r2) fa[r2]=r1;
}
bool judge(int r1,int r2){
r1=find(r1); r2=find(r2);
if(r1!=r2) return false;
else return true;
}
int main()
{
cin>>n>>m;//n=read(); m=read();
for(int i=1;i<=m;i++){
x[i]=read(); y[i]=read();
add(x[i],y[i]); add(y[i],x[i]);
}
k=read(); for(int i=1;i<=n;i++) fa[i]=i;
for(int i=1;i<=k;i++){
bui[i]=read(); vis[bui[i]]=1;
}
ans[k+1]=n-k;
for(int i=1;i<=m;i++){
if(!vis[x[i]]&&!vis[y[i]]&&!judge(x[i],y[i])){
un(x[i],y[i]); ans[k+1]--;
}
}
int que=ans[k+1];
for(int i=k;i>=1;i--){
vis[bui[i]]=0; que++;
for(int j=head[bui[i]];j!=0;j=t[j].next){
if(!vis[t[j].to]&&judge(bui[i],t[j].to)==false){
un(bui[i],t[j].to); que--;
}
}
ans[k]=que;
}
for(int i=1;i<=k+1;i++){
cout<<ans[i]<<endl;
}
return 0;
}
by Wf_yjqd @ 2023-03-04 21:20:32
你知道啥是反向建边么。。