POJ 1308 Is It A Tree?

题目地址

判断给定的结点是否构成一棵树。

注意:结点集合为空构成空树;有重复的边不是树;节点有指向自己的边不是树;树只有一个根节点;

思想:使用并查集。将添加的结点合并,最终只有一个结点。注意新加的结点b为a的长辈。

#include <iostream>
//#include <map>
using namespace std;
/*
  tree: 1. no cycle
  2. noly indegree==0
  3. else indegree==1
*/

const int size = 100000;
//map<int, int> hash;
int fa[size];
bool vis[size];
int Find(int x)
{
    if (x == fa[x])
       return x;
    return fa[x] = Find(fa[x]);
}

int main()
{
    int a, b;    
    int cas = 1;
    int yes = 1;
    int i, maxn;
    while (scanf("%d %d",&a,&b)!=EOF)
    {      
          if (a < 0 || b < 0) break; 
          
          if (0 == a && 0 == b)// 空树 
          {
               printf("Case %d is a tree.\n",cas++);     
               continue;
          }
          yes = 1;
          maxn = 0;
          for (i = 0; i < size; ++i)
          {
              fa[i] = i;
              vis[i] = 0;
          }
          
          if (a != b) 
              fa[b] = a;
          else yes = 0; // self-directed
           
          vis[b] = vis[a] = 1; 
          maxn = a > b? a :b;
          
          while (scanf("%d %d",&a,&b)!=EOF)
          {
                if (0 == a || 0 == b)
                   break;
                if (!yes || a== b)
                {
                    yes = 0; // self-directed
                    continue;
                }                
                vis[a] = vis[b] = 1;
                maxn = maxn>a?maxn:a;
                maxn = maxn>b?maxn:b;
                if (fa[b] != b || Find(a) == Find(b)) //b has more fa, b is a's father
                {
                   yes = 0;
                   //break;
                }
                else fa[b] = Find(a);
          }
          a = 0;
          for (i = 1; i <= maxn; ++i)
          {
              if (vis[i])
              {
                 if (Find(i) == i)
                    a++;
                 if (a > 1)
                 {
                    yes = 0;
                    break;
                 }    
              }
          }
          if (a != 1) yes = 0;
          printf("Case %d is ",cas++);
          if (yes) printf("a tree.\n");
          else printf("not a tree.\n");
    }
    //system("pause");
    return 0;
}

转载于:https://my.oschina.net/acemumu/blog/101922

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值