家族

来源:互联网 发布:传奇3数据库软件 编辑:程序博客网 时间:2024/06/08 09:38

若某个家族人员过于庞大,要判断两个是否是亲戚,确实还很不容易,现在给出某个亲戚关系图,求任意给出的两个人是否具有亲戚关系。 
规定:x和y是亲戚,y和z是亲戚,那么x和z也是亲戚。如果x,y是亲戚,那么x的亲戚都是y的亲戚,y的亲戚也都是x的亲戚。 

Input

第一行:三个整数n,m,p,(n<=50000,m<=50000,p<=50000),分别表示有n个人,m个亲戚关系,询问p对亲戚关系。以下m行:每行两个数Mi,Mj,1<=Mi,Mj<=N,表示Ai和Bi具有亲戚关系。接下来p行:每行两个数Pi,Pj,询问Pi和Pj是否具有亲戚关系。

Output

P行,每行一个’Yes’或’No’。表示第i个询问的答案为“具有”或“不具有”亲戚关系。

Sample Input

6 5 341 21 53 45 21 31 42 35 6

Sample Output

YesYesNo
题解:并查集套入,判断。(用while的查找老大,速度可以提高一些)
  • #include<cstdio>#include<iostream>using namespace std;int f[50009],n,m,p,a,b,ans[50009];int find(int x){    int k=x;    while(f[x]!=x) x=f[x];    while(f[k]!=x)    {        int temp=f[k];        f[k]=x;        k=temp;    }    return x;}void unionn(int x,int y){    f[y]=x;}int main(){    scanf("%d%d%d",&n,&m,&p);    for(int i=1;i<=n;i++) f[i]=i;    for(int i=1;i<=m;i++)    {        scanf("%d%d",&a,&b);        int temp1=find(a);        int temp2=find(b);        if(temp1!=temp2) unionn(temp1,temp2);    }    for(int i=1;i<=p;i++)    {        scanf("%d%d",&a,&b);        if(find(a)==find(b)) ans[i]=1;    }    for(int i=1;i<=p;i++)        if(ans[i]==1) printf("Yes\n");        else printf("No\n");    return 0;}