两道题类型一样,下面就以1029为例
题意:给你编号为1到n个钱币,其中有一个是假的,k次称量结果,判断并输出假币的编号,不能判断输出0。
分析:
1.等号‘=’两边全为真币。
2.假币不可能既偏重又偏轻。
3.几次不等的称量假币就出现几次。
AC代码:
#include<stdio.h>
#include<string.h>
#define max 1003
int mark[max];
struct node
{
int s;
char c[3];
int a[max>>1],b[max>>1];
}nod[103];
int main()
{
int n,k;
int i,j,l;
int t,x,x1,x2;
int eq;//等式的数量;
while(~scanf("%d%d",&n,&k))
{
memset(mark,0,sizeof(mark));
eq=0;
//输入;
for(i=0;i<k;i++)
{
scanf("%d",&nod[i].s);
for(j=0;j<nod[i].s;j++)
scanf("%d",&nod[i].a[j]);
for(j=0;j<nod[i].s;j++)
scanf("%d",&nod[i].b[j]);
scanf("%s",nod[i].c);
//记录相等的情况;
if(nod[i].c[0]=='=')
{
for(j=0;j<nod[i].s;j++)
mark[nod[i].a[j]]=mark[nod[i].b[j]]=1;
eq++;
}
else if(nod[i].c[0]=='<')
{
//不相等则变为一种情况;都变为 > 。
for(j=0;j<nod[i].s;j++)
{
t=nod[i].a[j];
nod[i].a[j]=nod[i].b[j];
nod[i].b[j]=t;
}
nod[i].c[0]='>';
}
}
t=0;
for(i=1;i<=n;i++)
if(mark[i]==0)
{
x1=x2=0;
for(j=0;j<k;j++)
if(nod[j].c[0]=='>')
{
for(l=0;l<nod[j].s;l++)
{
if(nod[j].a[l]==i)
x1++;
if(nod[j].b[l]==i)
x2++;
}
}
if(x1&&x2)//假币不可能既偏重又偏轻;
mark[i]=1;
else if(x1==k-eq&&x2==0||x1==0&&x2==k-eq)
{
//满足这个才可能是假币;
t++;
x=i;
}
}
if(t==1)
printf("%d\n",x);
else
printf("0\n");
}
return 0;
}