pku2192(并查集+枚举)
这题的话,跟食物链很相识,也是有三类,所以那个公式的话,还是一样的
题意是要找出里面唯一的一个judge,judge的特别就是他没有固定属于哪一类,所以只能枚举每一个人当judge的情况了
满足是唯一的judge的条件:
1)当然就是枚举完所有人,只有一个的时候,那就是唯一的了;
2)当此人是judge时,所有语句都成立,即不发生冲突
在这里题目还要出输出,在第几行判断该人是judge的,这个也蛮好理解的,此人之前的所有人作为judge时出现矛盾的行数的最大值就是就是我们判断的依据,
其实也可以这样想,判断当前面所以人不能成为judge的行数的最大,就是我们判断此人为judge的行数
当不止一个人可以成为judge是,输出Can not determine
当所有人都不能成为judge是,输出Impossible
#include<stdio.h>
#define MAXN 510
int f[MAXN],r[MAXN];
int a[2010],b[2010];
int find(int x)
{
if(x==f[x])
return f[x];
int t=find(f[x]);
r[x]=(r[x]+r[f[x]])%3;
f[x]=t;
return f[x];
}
int Union(int x,int y,int d)
{
int a=find(x);
int b=find(y);
if(a==b)
{
if((r[x]+d)%3==r[y])
return 1;
else return 0;
}
else
{
f[b]=a;
r[b]=(r[x]-r[y]+d+3)%3;
}
return 1;
}
int main()
{
int n,m,i,j,flag,num,d,max,k;
char c[2001];
while(scanf("%d %d",&n,&m)!=EOF)
{
for(j=1;j<=m;j++)
scanf("%d%c%d",&a[j],&c[j],&b[j]);
num=max=0;
for(i=0;i<n;i++)
{
for(k=0;k<n;k++)//初始化
{
f[k]=k;
r[k]=0;
}
for(j=1;j<=m;j++)
{
if(a[j]==i||b[j]==i)//当我们以i为judge时,输赢都无所谓,所以不合并,应该说是不能合并
continue;
if(c[j]=='=')
d=0;
else if(c[j]=='<')
d=1;
else d=2;
if(Union(a[j],b[j],d)==0)
break;
}
if(j==m+1)//所有语句都正确
{
num++;
flag=i;
}
else
{
if(j>max)
max=j;
}//
if(num>=2)
break;
}
if(num==0)
printf("Impossible\n");
else if(num==1)
printf("Player %d can be determined to be the judge after %d lines\n",flag,max);
else printf("Can not determine\n");
}
return 0;
}

浙公网安备 33010602011771号