poj 2492 A Bug's Life(关系并差集)

http://poj.org/problem?id=2492

题意:给出几组不同性别的虫子,判断是否存在同性恋

关系并差集,用r[]记录与根节点的关系,r[i]==0与根节点同性,r[i]==1与根节点异性

x以a为根节点,y以b为根节点,根据x,y异性的的关系,让b以a为根节点时,得出 r[y]+(待求值)r[b]+r[x]=1,(x,y异性,关系为1,y到b的关系,加上b到a的关系,加上a到x的关系,就是x与y的关系),则r[b]=1-r[x]-r[y],因为,r[]只有0,1两个数值,所以 r[b]=(r[x]+r[y]+1)%2;

参考blog http://www.haogongju.net/art/1579095

代码:

#include<iostream>
#include<cstdio>
#include<cstring>
#include<string>
#define nMAX 2005
using namespace std;
int f[nMAX],r[nMAX],n;
void make_set()
{
    int i;
    for(i=1;i<=n;i++)
        f[i]=i,r[i]=0;
}
int find_root(int x)
{
    int temp;
    if(x!=f[x])
    {
        temp=f[x];
        f[x]=find_root(f[x]);
        r[x]=(r[x]+r[temp])%2;
    }
    return f[x];
}
void union_set(int x,int y,int rx,int ry)
{
    f[ry]=rx;
    r[ry]=(r[x]+r[y]+1)%2;
}
int main()
{
    int CASE,ca,m,x,y;
    bool fg;
    scanf("%d",&CASE);
    for(ca=1;ca<=CASE;ca++)
    {
        scanf("%d%d",&n,&m);
        make_set();
        fg=0;
        while(m--)
        {
            scanf("%d%d",&x,&y);
            if(fg)continue;
            int rx=find_root(x);
            int ry=find_root(y);
            if(rx==ry)
            {
                if(r[x]==r[y])
                {
                    fg=1;
                    continue;
                }
            }
            else union_set(x,y,rx,ry);
        }
        printf("Scenario #%d:\n",ca);
        if(fg)printf("Suspicious bugs found!\n\n");
        else printf("No suspicious bugs found!\n\n");
    }
    return 0;
}

  

posted @ 2012-08-13 09:20  快乐.  阅读(140)  评论(0编辑  收藏  举报