poj1308 Is it a tree?

这个并查集又是个一个很模板的数据结构一个查找函数,一个合并函数,然后为了减小树的深度,需要压缩路径,这里推荐一个博客,我觉得写得特别详细;之后有时间要把二分路径压缩好好学一学;压缩路径也是优化算法的很重要的途径,然后做的时候我去查了一些资料,然后整理了一下思路,环,森林是不可以的,0 0 是树 然后自己指向自己也是不可以的;我在做的时候也没有仔细想过数组赋值的事情,所以第一次就wa了。

http://blog.csdn.net/youngyangyang04/article/details/7453564

#include<iostream>
#include<cstdio>
#include<cstring>
#include<set>
using namespace std;
const int maxn=200;
bool fa[maxn];
int jihe[maxn];
void makeset(void)
{
    for(int i=1;i<105;i++)
        jihe[i]=i;
}
int find(int x)
{
    return jihe[x] == x ? x : (jihe[x] = find(jihe[x]));
}
void join(int x,int y)
{
    int fx=find(x),fy=find(y);
    if(fx==fy) return;
        jihe[fy]=fx;
}
int main()
{
    int a,b,c,d;c=1;
    while(scanf("%d%d",&a,&b)!=EOF)
    {
        if(a==-1&&b==-1)
            break;
        if(a==0&&b==0)
        {
            printf("Case %d is a tree.
",c++);
            continue;
        }
        makeset();
        memset(fa,false,sizeof(fa));
        fa[a]=fa[b];
        d=b;
        bool tree=true;
        if(a==b) tree=false;
        else join(a,b);
        while(scanf("%d%d",&a,&b)&&a!=0&&b!=0)
        {
            fa[a]=fa[b]=true;
            if(find(a)==find(b)) tree=false;
            join (a,b);
        }
        for(int i=1;i<100;i++)
        {
            if(fa[i]&&find(jihe[i])!=find(jihe[d]))
            tree=false;
        }
        if(tree)
            printf("Case %d is a tree.
",c++);
        else
            printf("Case %d is not a tree.
",c++);
    }
    return 0;
}

  

原文地址:https://www.cnblogs.com/yintoki/p/5688379.html