Find them, Catch them
题目大意:在某个城市里有两个黑帮团伙,现在给出n个人和m组关系,问任意两个人是否在同一个黑帮团伙中。
第一行输入一个t,表示案例数
接下来一行输入人数n和关系对m。
接下来m行为关系对:
输入D x y代表x于y不在一个团伙里
输入A x y要输出x与y是否在同一团伙或者不确定他们在同一个团伙里。
这也是一道并查集的题目,和研究虫子是否存在同性恋的问题相似。这里就是研究任意两个人是否在同一个黑帮里。不过这道题在输入的时候要做一些小小的处理。因为每行会输入一个字母A或D,所以在每行输入完成后都要加一个getchar()函数,避免出错。这里也是用到了ans[]数组来记录每个人属于哪个黑帮,最后通过比较ans[]判断是否在同一个黑帮中。这里要去每次输入一个A就要判断一次。
Sample Input
1 5 5 A 1 2 D 1 2 A 1 2 D 2 4 A 1 4
Sample Output
Not sure yet. In different gangs. In the same gang.
代码:
#include<stdio.h>
#define MAX 100001
int ans[MAX],tree[MAX];
void init(int n)
{
int i;
for(i=1;i<=n;i++)
{
ans[i]=0;
tree[i]=i;
}
}
int getfather(int x)
{
int rt;
if(x!=tree[x])
{
rt=getfather(tree[x]);
ans[x]=ans[x]^ans[tree[x]];
return tree[x]=rt;
}
return x;
}
void Union(int x,int y){
int fx,fy;
fx=getfather(x);
fy=getfather(y);
tree[fx]=fy;
ans[fx]=~(ans[y]^ans[x]);
}
int main()
{
int i,j,n,m,a,b,t;
char c;
scanf("%d",&t);
for(j=1;j<=t;j++)
{
scanf("%d %d\n",&n,&m);
init(n);
for(i=1;i<=m;i++)
{
scanf("%c %d %d",&c,&a,&b);
getchar();
if(c=='D')
{
Union(a,b);
}
else
{
if(n==2)
printf("In different gangs.\n");
else if(getfather(a)==getfather(b))
{
if(ans[a]==ans[b])
printf("In the same gang.\n");
else
printf("In different gangs.\n");
}
else
printf("Not sure yet.\n");
}
}
}
return 0;
}