1 条题解

  • 0
    @ 2026-1-30 19:08:54
    #include<bits/stdc++.h>
    #define fa(p) tr[p].fa
    #define lc(p) tr[p].ch[0]
    #define rc(p) tr[p].ch[1]
    #define nr(p) (lc(fa(p))==p||rc(fa(p))==p)
    using namespace std;
    typedef long long ll;
    const int mxn=2e5+10;
    int n,m,q,fa[mxn],sz[mxn];
    int find(int x){
    	return fa[x]=(fa[x]==x?x:find(fa[x]));
    }
    void merge(int x,int y){
    	x=find(x);y=find(y);if(x==y)return ;
    	fa[y]=x;
    	sz[x]+=sz[y];
    }
    struct N{
    	int ch[2],fa,sz,la;
    }tr[mxn];
    void pushup(int p){
    	tr[p].sz=tr[lc(p)].sz+tr[rc(p)].sz+1;
    }
    void pushdown(int p){
    	if(tr[p].la){
    		swap(lc(p),rc(p));
    		tr[lc(p)].la^=1;
    		tr[rc(p)].la^=1;
    		tr[p].la=0;
    	}
    }
    void rotate(int x){
    	int y=fa(x),z=fa(y),k=rc(y)==x;
    	if(nr(y))tr[z].ch[rc(z)==y]=x;fa(x)=z;
    	tr[y].ch[k]=tr[x].ch[k^1];fa(tr[x].ch[k^1])=y;
    	tr[x].ch[k^1]=y;fa(y)=x;
    }
    void pushall(int x){
    	if(nr(x))pushall(fa(x));
    	pushdown(x);
    }
    void splay(int x){
    	pushall(x);
    	while(nr(x)){
    		int y=fa(x),z=fa(y);
    		if(nr(y))((rc(y)==x)^(rc(z)==y))?rotate(x):rotate(y);
    		rotate(x);
    	}
    }
    void access(int x){
    	for(int y=0;x;){
    		splay(x);
    		rc(x)=y;
    		pushup(x);
    		y=x;x=fa(x);
    	}
    }
    void mkrt(int x){
    	access(x);
    	splay(x);
    	tr[x].la^=1;
    }
    void split(int x,int y){
    	mkrt(x);
    	access(y);
    	splay(y);
    }
    int fdrt(int x){
    	access(x);
    	splay(x);
    	while(lc(x))pushdown(x),x=lc(x);
    	splay(x);
    	return x;
    } 
    void dfs(int x,int tp){
    	if(!x)return ;
    	merge(tp,x);
    	if(lc(x))dfs(lc(x),tp);
    	if(rc(x))dfs(rc(x),tp);
    	lc(x)=rc(x)=0;
    	pushup(x);
    }
    void add(int x,int y){
    	x=find(x);y=find(y);
    	if(x==y)return ;
    	mkrt(x);
    	if(fdrt(y)!=x){
    		fa(x)=y;
    	}
    	else{
    		split(x,y);
    		dfs(y,y);
    	}
    }
    int ask(int x,int y){
    	x=find(x);y=find(y);
    	if(x==y){
    		return sz[y];
    	}
    	else{
    		return -1;
    	}
    }
    int main(){
    	ios::sync_with_stdio(0);
    	cin.tie(0);
    	cin>>n>>m>>q;
    	for(int i=1;i<=n;i++){
    		fa[i]=i;
    		sz[i]=1;
    		tr[i].sz=1;
    	}
    	for(int i=1,x,y;i<=m;i++){
    		cin>>x>>y;
    		add(x,y);
    	}
    	while(q--){
    		int x,y;
    		cin>>x>>y;
    		add(x,y);
    		int ans=ask(x,y);
    		if(~ans)cout<<ans<<'\n';
    		else cout<<"No\n";
    	}
    	return 0;
    }
    
    
    
    • 1

    【动态树 LCT】BZOJ4998 星球联盟

    信息

    ID
    6667
    时间
    1000ms
    内存
    512MiB
    难度
    9
    标签
    递交数
    17
    已通过
    2
    上传者