关于这类取火柴问题,在掌握了规则的前提下,先手必赢。
所以在电脑作为后手的前提下,只能祈祷玩家不懂规则,第一步就取错数目,之后就是电脑必赢了。
题目如下:
#include <stdio.h>
#include <Windows.h>
#define fire_wood_all 22//最初火柴数目
#define fire_wood_get 4//一次能拿几根
int fire_wood = fire_wood_all;//剩下火柴数
int player_get;
int computer_get = 0;
int is_live = 1;//是否继续程序
void computer() {
//根据规则,试图获取必胜数目
computer_get = fire_wood;
if (computer_get > (fire_wood_get + 1))
computer_get %= (fire_wood_get + 1);
--computer_get;
if (computer_get < 1)//如果玩家先手掌握了规则,那么computer_get必为0,这里是妥协的代码,等着玩家自己犯错
computer_get = 1;
fire_wood -= computer_get;//减少
}
int main() {
while (1) {
system("cls");
printf("现有%d根火柴,两人轮流取,每人每次可以取1至%d根,不可多取,也不能不取,谁取最后一根火柴谁输。\n", fire_wood_all, fire_wood_get);
if (computer_get)
printf("电脑拿取了%d根\n", computer_get);
printf("当前剩余火柴数:%d\n", fire_wood);
if (!is_live)
break;
in_again:
printf("你要拿几根(1~%d):",fire_wood_get);
scanf_s("%d", &player_get);
if (player_get < 1 || player_get>fire_wood_get || player_get > fire_wood) {
printf("输入有误,请重新输入\n");
goto in_again;
}
fire_wood -= player_get;//减少
if (fire_wood < 2)
is_live = 0;
if (is_live) {//如果还要继续
computer();//电脑获取
player_get = -1;
if (fire_wood < 2)
is_live = 0;
}
}
if (player_get > 0)
printf("玩家获胜\n");
else
printf("电脑获胜\n");
}
结果: