巴什博奕、威佐夫博弈、尼姆博奕、斐波那契博弈
组合博弈基础:三大基础博弈+斐波那契博弈
网上来证明这 3+1 种博弈的已经够多了,但有时直接的证明不一定会理解,最后还是要用刷题来间接理解。其实我个人的观点是,证明这种考量思维的细活完全可以当作拓展知识面、兴趣爱好什么的,一旦较真便很难看下去,平时动动笔玩玩博弈也不是不可以。所以这里我不多证明博弈,重在做题和结论。这篇仅仅是入门。
- 一、巴什博奕
取石子游戏一
有一种有趣的游戏,玩法如下:
玩家: 2人;
道具:N 颗石子;
规则:
游戏双方轮流取石子;
每人每次取走若干颗石子(最少取1 颗,最多取K颗);
石子取光,则游戏结束;
最后取石子的一方为胜。
假如参与游戏的玩家都非常聪明,问最后谁会获胜?
输入格式
输入仅一行,两个整数 N和 K。
输出格式
输出仅一行,一个整数,若先手获胜输出 1,后手获胜输出 2。
样例
样例输入
23 3
样例输出
1
#include <bits/stdc++.h>
using namespace std;
int n, k;
int main() {
scanf("%d %d", &n, &k);
if (n % (k + 1) == 0) cout << "2";
else cout << "1";
return 0;
}
规律总结:(PS:百度上有,直接复制了)
只有一堆n个物品,两个人轮流从这堆物品中取物,规定每次至少取一个,最多取m个,最后取光者得胜。当n和m取值为多少时,先手必胜?如果n=(m+1)r+s,(r为任意自然数,1 ≤ s≤m那么先取者要拿走s个物品,如果后取者拿走k(≤m)个,那么先取者再拿走m+1-k个,结果剩下(m+1)(r-1)个,以后保持这样的取法,那么先取者肯定获胜。
所以判断先手必胜的条件: (n % (k + 1) != 0)
过于简单,不说明了。
- 二、威佐夫博弈
例题类型:
有两堆各若干个物品,两个人轮流从某一堆取任意个或同时从两堆中取同样多个物品,规定每次至少取一个,多者不限,最后取光者得胜。
威佐夫博弈不同于Nim博弈与巴什博奕,它的特殊之处在于不能将两堆石子分开分析。
有一篇证明的挺好的,也有例题:博弈论之威佐夫博弈
证明并不烦,但不多解释。这里直接给出结论
*若两堆物品的初始值为(x,y),且x<y,则另z=y-x;记w=(int)[ ( (sqrt(5)+1) /2 )z ];若w=x,则先手必败,否则先手必胜。
#include<iostream>
#include<cmath>
using namespace std;
int main()
{
int x,y;
cin>>x>>y;
int z=abs(y-x);
if((int)(((sqrt(5)+1)/2)*z)==min(x,y))
cout<<"后手必胜"<<endl;
else
cout<<"先手必胜"<<endl;
}
它引出了一个重要概念,博弈中经常用:奇异局势
三个性质:
1、任何自然数都包含在一个且仅有一个奇异局势中。
2、任意操作都可将奇异局势变为非奇异局势。
3、采用适当的方法,可以将非奇异局势变为奇异局势。
单纯放出有点迷,但在这里奇异局势指:
我们用(a[k],b[k])表示两堆物品的数量并称其为局势,显然(0,0)为必输局势,这种必输局势我们称为奇异局势。
前几个奇异局势是:(0,0),(1,2),(3,5),(4,7),(6,10),(8,13),(9,15),(11,18),(12,20)
a[k]为前k-1中的a[i]b[i]中未出现的最小非负整数 , b[k]=a[k]+k (a[0]=b[0]=0)
- 三、尼姆博弈
这个最有意思,要出题全是这类,有时会和巴什博奕相结合。之后我会这里一些尼姆博弈的变形体。这里先给出基础的。
例题:
给定n堆石子,两位玩家轮流操作,每次操作可以从任意一堆石子中拿走任意数量的石子(可以拿完,但不能不拿),最后无法进行操作的人视为失败。
问如果两人都采用最优策略,先手是否必胜。
结论:若a1^a2…an==0 则先手必败。
#include<bits/stdc++.h>
using namespace std;
int main(){
int a1 = 2 , a2 = 3 ;
if(a1^a2==0) puts("Win");
else puts("Lose");
return 0;
}
特征:
1.有两名选手;
2.两名选手交替操作,每次一步,每步都是在有限的合法集合中选取一种进行;
3.在任何情况下,合法操作只取决于情况本身,与选手无关;
4.游戏的败北条件为:当某位选手需要进行操作时,当前没有任何可以执行的合法操作,则该选手败北。
所以它有很多变形题。有点像背包问题了,不过本质抓住就可以了。
- 四、斐波那契博弈
有一堆石子,两个人轮流从其中取走一定的石子,取走最后所有石子的人为赢家,不过得遵循如下规则:
1.第一次取不能取完,至少取1颗.
2.从第二次开始,每个人取的石子数至少为1,至多为对手刚取的石子数的两倍。
结论:当n为Fibonacci数时,先手必败。否则先手必败