并查集初步

题目:HDU 1213

题意就是有一群人要去吃饭,但是不认识的不能坐在一起,这就要我们将认识的人合并……

赤裸裸的并查集。但是开始有个天真的想法:

用一个set数组记录,每次将有关系的人的值变为前一个人的值。

然后仔细想一想明显是不行的……

比如这个数据:1 - 2 , 3 - 4 , 2 - 3

对于4个人的这个数据显然只需要一张桌子!因为都认识。。。。可是如果用上面的方法将会得到错误的答案!

所以只能用并查集了~~

不说了,贴代码+注释:

#include <cstdio>
#include <algorithm>

int set[1050];

int find(int x)
{
    int t = x;
    while (t != set[t]) t = set[t];
    return t;
}

void Union(int x , int y)
{
     int a = find(x);
     int b = find(y);
     set[a] = b;
}

int main()
{
    int T , n , m , a , b;
    int i , ans;
    
    scanf("%d" , &T);
    while (T --)
    {
         scanf("%d%d" , &n , &m);
         for (i = 1 ; i <= n ; i ++)
            set[i] = i;
         ans = 0;
         for (i = 0 ; i < m ; i ++)
         {
             scanf("%d%d" , &a , &b);
             if (find(a) != find(b))  // 看看是否属于同一个集合
             {
                 ans ++;  // 若不是则ans + 1
                 Union(a , b);   // 合并起来
             }
         }
         printf("%d\n" , n - ans);
    }
}

对于数据:

1

4 3

1 2

3 4

2 3

得到的树是这个样子的:

posted on 2013-02-26 17:49  Hmm  阅读(135)  评论(0编辑  收藏  举报

导航