BZOJ P1370 [Baltic2003] 团伙【并查集】

感觉这道题和 N O I P 关押罪犯很相像?

把每个人看成一个点,然后人与人之间的关系看成边,首先把点 i 拆成两个点 i i + n ,如果两个人是朋友的话直接连边就好了,否则的话就 x y + n 一条边, y x + n 一条边,最后统计一下答案就可以了。

参考代码:

#include <cstdio>
const int Max=1e3+5;
char CH[3];
int N,M,Ans,F[Max<<1],Vis[Max<<1];
int Find(int X){
    return F[X]==X?X:F[X]=Find(F[X]);
} 
int main(){
    int I,J,K;
    scanf("%d%d",&N,&M);
    for(I=1;I<=(N<<1);I++){
        F[I]=I;
    }
    for(I=1;I<=M;I++){
        int X,Y;
        scanf("%s%d%d",CH,&X,&Y);
        if(CH[0]=='F'){
            int Fx=Find(X),Fy=Find(Y);
            if(Fx!=Fy){
                F[Fx]=Fy;
            }
        } else {
            int Fx=Find(X+N),Fy=Find(Y);
            if(Fx!=Fy){
                F[Fy]=Fx;
            }
            Fx=Find(X),Fy=Find(Y+N);
            if(Fx!=Fy){
                F[Fx]=Fy;
            }
        }
    }
    for(I=1;I<=N;I++){
        int Fx=Find(I);
        if(Vis[Fx]==0){
            Vis[Fx]++;Ans++;
        }
    }
    printf("%d",Ans);
}

猜你喜欢

转载自blog.csdn.net/yanzhenhuai/article/details/81167440