码迷,mamicode.com
首页 > 其他好文 > 详细

hdoj1325 Is It A Tree?

时间:2015-05-19 22:48:20      阅读:171      评论:0      收藏:0      [点我收藏+]

标签:hdoj1325      并查集   

hdoj1325 题目链接

题意:
多组测试数据, 每组数据有多个数对, 表示一条有向边(即第一个数是第二个数的父节点), 以 0,0 为一组测试数据结束标志。当输入-1,-1时测试结束。 从那些给出的信息中判断是否是一棵树。
分析:
1、只可以有一个根节点, 也可以是一个点都没有的空树;
2、除了根节点, 每个点只有一个父节点。
3、因为只可以有一个父节点, 所以我们可以把一个合法的关系对(一个父亲节点与孩子节点对)合并到一个集合里, 他们的父节点都标记为所属树的根节点, 那样我们方便判断是否成环。
4、判断是否成环, 成环不可以。
5、 还有一个很衰的地方, 注意不光输入-1,-1 测试结束, 只要输入两个数都小于0就结束。


#include<iostream>
#include<cstdio>
#include<string.h>
#include<math.h>
#include<algorithm>
using namespace std;

const int N = 10005;

int a, b, n, mi, mx, sum, flag, v[N], pre[N];
int find(int x)//寻找x所属的树的根节点
{
    int r, i, j;
    r = x; i = x;
    while(r != pre[r])
        r = pre[r];
    while(pre[i] != r)
    {
        j = pre[i];
        pre[i] = r;
        i = j;
    }
    return pre[x];
}
int main()
{
    n = 0;
    while(scanf("%d%d", &a, &b) != EOF)
    {
        memset(v, 0, sizeof(v));//记录所涉及的点
        for(int i = 1; i <= N; i++)
            pre[i] = i;
        if(a < 0 && b < 0) break;
        else if(a == 0 && b == 0)//特殊处理, 空树
        {
            printf("Case %d is a tree.\n", ++n);
            continue;
        }
        pre[b] = a;
        v[a] = 1;
        v[b] = 1;
        mi = min(a, b);
        mx = max(a, b);
        flag = 1;
        while(scanf("%d%d", &a, &b) != EOF)
        {
            if(a == 0 && b == 0) break;
            if(mx < a || mx < b) mx = max(a, b);
            if(mi > a || mi > b) mi = min(a, b);
            v[a] = 1;
            v[b] = 1;
            if(flag == 1)
            {
                int fx = find(a);
                int fy = find(b);
                if((fy != b) || (fy == fx))//若构成环, 或孩子节点已经有父节点了, 那就是不合法的边
                    flag = 0;
                else if(fy == b && fy != fx)//如果不构成环并且没有父亲节点, 那就是合法的, 加入
                    pre[b] = fx;
            }
        }
        int sum = 0;
        if(flag == 1)
        {
            for(int i = mi; i <= mx; i++)//判断是否存在多棵树
            {
                if(v[i] == 1)
                {
                    int fx = find(i);
                    if(fx == i)
                    {
                        sum++;
                        if(sum > 1)
                        {
                            flag = 0;
                            break;
                        }
                    }
                }
            }
        }
        if(flag == 1)
            printf("Case %d is a tree.\n", ++n);
        else if(flag == 0)
            printf("Case %d is not a tree.\n", ++n);
    }
    return 0;
}

hdoj1325 Is It A Tree?

标签:hdoj1325      并查集   

原文地址:http://blog.csdn.net/wangdan11111/article/details/45849329

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!