第22题:
有4张红色的牌和4张蓝色的牌,主持人先拿任意两张,
再分别在A、B、C三人额头上贴任意两张牌,
A、B、C三人都可以看见其余两人额头上的牌,
看完后让他们猜自己额头上是什么颜色的牌,
A说不知道,B说不知道,C说不知道,然后A说知道了。
请教如何推理,A是怎么知道的。如果用程序,又怎么实现呢?
此题如果用计算机程序来模拟,那么肯定是用枚举,所有可能性来进行循环处理
分析:
4张 r 4张b
有以下3种组合:
rr bb rb
1.B,C全是一种颜色
B C A
bb.rr bb.rr
2.
B C A
bb rr bb/RR/BR,=>A:BR
rr bb =>A:BR
3.
B C A
BR BB RR/BR, =>A:BR
//推出A:BR的原因,
//如果 A是 RR,
//那么,当ABC都说不知道后,B 最后应该知道自己是BR了。
//因为B 不可能 是 RR或BB。
4.
B C A
BR BR BB/RR/BR
//推出A:BR的原因
//i、 如果,A是 BB,那么B=>BR/RR,
//如果B=>RR,那么一开始,C就该知道自己是BR了(A俩蓝,B俩红)。(如果C.A俩蓝,那么B就一开始知道,如果C.B俩红,那么A一开始就知道,所以,论证前头,当B=>RR,那么一开始,C就该知道自己是BR)。
//如果B=>BR,那么,同样道理,C一开始也该知道自己是BR了。
//ii、 如果A是RR....
//iii、最后,也还是推出=>A:BR
源代码如下:
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
char all[4][3]={"bb","br","rr"};
int main()
{
int i,j,k;
for(i=0;i<3;i++)
for(j=0;j<3;j++)
for(k=0;k<3;k++)
{
int blue=0,red=0;
if(all[i][0]=='b')
blue+=1;
else
red+=1;
if(all[i][1]=='b')
blue+=1;
else
red+=1;
if(all[j][0]=='b')
blue+=1;
else
red+=1;
if(all[j][1]=='b')
blue+=1;
else
red+=1;
if(all[k][0]=='b')
blue+=1;
else
red+=1;
if(all[k][1]=='b')
blue+=1;
else
red+=1;
if(blue<4&&red<4)
{
if(strcmp(all[i],all[j])>0)
{
char word[3];
sprintf(word,"%s",all[i]);
sprintf(all[i],"%s",all[j]);
sprintf(all[j],"%s",word);
}
if(strcmp(all[i],all[k])>0)
{
char word[3];
sprintf(word,"%s",all[i]);
sprintf(all[i],"%s",all[k]);
sprintf(all[k],"%s",word);
}
if(strcmp(all[j],all[k])>0)
{
char word[3];
sprintf(word,"%s",all[j]);
sprintf(all[j],"%s",all[k]);
sprintf(all[k],"%s",word);
}
printf("%s %s %s \n",all[i],all[j],all[k]);
}
}
system("pause");
return 0;
}
最后其实有个重点就是,根据循环出来的B C状态,来推A的可能性(即相加<=4即可),如果为2,那么说明A有两种可能的情况,则A无法确定,不输出,否则 ,输出答案,后面是对A B C进行排序
最后得到只可能有一种答案 BB BR RR