CF1167C News Distribution Weighted disjoint-set

https://codeforces.com/contest/1167/problem/C

The meaning of problems: n users there are m groups, each user may appear in a plurality of packets, the packet also allows a null. Each user can message to everyone in the same group, seeking up to each user to send messages to the number of individuals.

Ideas: Weighted disjoint-set, a tree of any one person can pass the message to everyone else on the tree. rk array of maintaining the point belongs tree has a number of nodes (including the root). rk output value of each node is the answer

#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const int maxn=5e5+5;
int pa[maxn];
int rk[maxn];

int find(int x){
    return pa[x]==x? x:pa[x]=find(pa[x]);
}

void unite(int a,int b){
    a=find(a),b=find(b);
    if(a==b) return;
    if(rk[a]<rk[b]) {
        pa[a]=b;
        rk[b]+=rk[a];
    }
    else{
        pa[b]=a;
        rk[a]+=rk[b];
    }
}

int main(){
    //freopen("datain.txt", "r", stdin);
    ios::sync_with_stdio(0);
    cin.tie(0);
    int n,m;
    cin>>n>>m;
    for(int i=0;i<n;i++) pa[i]=i,rk[i]=1;
    for(int i=0;i<m;i++){
        int k;cin>>k;
        if(k==0) continue;
        int last=-1,cur;
        cin>>last; last;
        for(int j=1;j<k;j++){
            cin>>cur; cur;
            unite(cur,last);
        }
    }
    for(int i=1;i<=n;i++){
        cout<<rk[find(i)]<<' ';
    }
    //cout<<rk[find(0)];
    cout<<endl;
}

 

Guess you like

Origin www.cnblogs.com/hanker99/p/10968444.html