hdu 2473 并查集
思路:每次合并时,都是给一个虚拟的根。
#include<map> #include<Set> #include<cmath> #include<queue> #include<cstdio> #include<vector> #include<string> #include<cstdlib> #include<cstring> #include<iostream> #include<algorithm> #define Maxn 100010 #define Maxm 2000010 #define LL __int64 #define Abs(x) ((x)>0?(x):(-x)) #define lson(x) (x<<1) #define rson(x) (x<<1|1) #define inf 0x3f3f3f3f #define Mod 1000000007 using namespace std; int Set[Maxn*2],cnt,vi[Maxn*2],n; void init() { for(int i=0;i<Maxn*2;i++) Set[i]=i; memset(vi,0,sizeof(vi)); cnt=n; } int Find(int x) { if(Set[x]!=x) Set[x]=Find(Set[x]); return Set[x]; } void merg(int a,int b) { int x,y; x=Find(a); y=Find(b); if(Set[x]==a&&Set[y]==b){ Set[x]=++cnt,Set[y]=cnt; return ; } if(Set[x]==Set[y]) return ; if(x<=n) Set[x]=y; else Set[y]=x; } int main() { int m,i,j,u,v,Case=0; char str[3]; while(scanf("%d%d",&n,&m),n||m){ init(); for(i=1;i<=m;i++){ scanf("%s",str); if(str[0]=='M'){ scanf("%d%d",&u,&v); merg(u,v); } else{ scanf("%d",&u); Set[u]=u; } } int ans=0; for(i=0;i<n;i++){ u=Find(i); if(!vi[u]){ ans++; vi[u]=1; } } printf("Case #%d: %d\n",++Case,ans); } return 0; }