题目链接:http://acm.split.hdu.edu.cn/showproblem.php?pid=1213
对这个问题抽象之后,就是要求进行若干次union操作之后,还会剩下多少颗树(或者说还剩下多少Connected Components)。反映到这个例子中,就是要求有多少“圈子”。其实,这也是社交网络中的最基本的功能,每次系统向你推荐的那些好友一般而言,会跟你在一个“圈子”里面,换言之,也就是你可能认识的人,以并查集的视角来看这层关系,就是你们挂在同一颗树上
/*用原始连通分量数n 减去 有效的合并次数。
即每次合并两个连通分量就会使得总的分量数目减少1*/
#include <iostream>
#include <cstring>
using namespace std;
const int maxn=1000+5;
int fa[maxn];
int Find(int x)
{
if(fa[x]==-1)
return x;
return fa[x]=Find(fa[x]);
}
int mix(int x,int y)
{
int fx=Find(x);
int fy=Find(y);
if(fx!=fy)
{
fa[fx]=fy;
return 1;
}
return 0;
}
int main()
{
int t,n,m,x,y;
cin>>t;
while(t--)
{
cin>>n>>m;
memset(fa,-1,sizeof(fa));
int ans=n;
while(m--)
{
cin>>x>>y;
ans-=mix(x,y);
}
cout<<ans<<endl;
}
return 0;
}