人机博弈:
现有21根火柴。每次只能取走1~4根。取走最后一根火柴的人输。人先取,计算机后取。要求设计一个程序进行人机对弈,使得计算机一方为”常胜将军“。
思路分析:
(巴什博弈)具体
n根火柴,一次最多m根。
n=(m+1)*r+s;
// r = n/(m+1) , s=n%(m+1)
-
(s!=0)
-
(站在先手的角度)若想先手取完火柴,则先手第一次取s个,之后后手出k个的话,先手就取(m+1-k)根。这就是把多余的s取完,再每一回合解决掉m+1就可以了。
-
(站在后手的角度)若想后手取完火柴,不可能。
-
(s==0)
-
(站在先手的角度)若想先手取完火柴,不可能。
-
(站在后手的角度)若想后手取完火柴,先手第一次取k个,后手就取(m+1-k)根。这就是每每一回合解决掉m+1就可以了。
此题:情况特殊
要求s=21%(4+1)=1!=0,要在后手的角度上考虑先手取完,跟以上庆幸不太符合。但由于s刚好等于1,故后手可根据先手的取数,每个回合解决掉(m+1),剩余1个必由先手取完。
#include<iostream>
#include<algorithm>
using namespace std;
const int N=10;
int main()
{
//规则说明
printf("-----------规则说明------------\n");
printf("现有21根火柴。\n每次只能取走1~4根。\n取走最后一根火柴的人输\n\n");
printf("--------人机对弈现在开始-------\n");
//游戏开始
for(int solo,computer,total=21;;){
printf("请输入您要取的火柴数:");
scanf("%d",&solo);
if(total==1){
printf("Sorry,you lost!");
break;
}
total=total-5;
printf("计算机取火柴%d根\n剩余火柴树:%d\n\n",5-solo,total);
}
}