/**
hdoj1325 zoj1268 nylg129
http://acm.hdu.edu.cn/showproblem.php?pid=1325
---------------------------------------------------
HuHanwu
2012-7-12
并查集快速判断每次输入是破坏树的性质
时间复杂度: o(n) n为节点的个数
---------------------------------------------------
*/
#include <iostream>
#include <cstdio>
#include <cstring>
using namespace std;
#define MAXN 1000002
int p[MAXN]; //存放父亲节点 只要存在父亲节点则此节点一存在某棵树中
int find(int x){ return p[x]==x ? x :(p[x]=find(p[x]));} //查找父亲节点并压缩路径
int main()
{
int a,b,tree_num,t=0,father_a,father_b,TF;//tree_num 保存当前的树的棵数
while(~scanf("%d%d",&a,&b) && a!=-1)
{
tree_num=TF=1;
if(a==0)
{
printf("Case %d is a tree.\n",++t);
continue;
}
if(a==b)
TF=0;
else
{
memset(p,0,sizeof(p)); //用 0 初始化所有节点的父亲节点
p[a]=p[b]=a;
}
while(~scanf("%d%d",&a,&b) && a!=0)
{
if(TF==0 ) // 只要已经判断出该森林已经不是树
continue;
if(p[b]!=0) // b 节点已经存在
{
father_b=find(b);
if(b!=father_b) // b 节点不是树根就不可以连成一棵树
{
TF=0;
continue;
}
else
{
if(p[a]!=0) // a b 节点都存在则树的的棵数-1
{
father_a=find(a);
if(father_b==father_a)
{
TF=0;
continue;
}
p[father_b]=father_a;
tree_num--;
}
else //a 节点不存在 而 b 节点存在且为跟节点
p[b]=p[a]=a;
}
}
else
{
if(p[a]==0) // a b 节点都不存在则树的棵数+1
{
p[a]=p[b]=a;
tree_num++;
}
else //a 节点存在 而 b 节点不存在
p[b]=find(a);
}
}
printf("Case %d ",++t);
if(TF==0)
{
printf("is not a tree.\n");
continue;
}
if(tree_num==1) // 树的棵数是否为1
printf("is a tree.\n");
else
printf("is not a tree.\n");
}
return 0;
}
/*
zoj poj nyoj 都过了 就是hdoj 错误答案
跪求大神指点迷津........
*/