本文主要是介绍POJ1067 取石子游戏(博弈论),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
取石子游戏
Time Limit: 1000MS | Memory Limit: 10000K | |
Total Submissions: 36633 | Accepted: 12396 |
Description
Input
Output
Sample Input
2 1 8 4 4 7
Sample Output
0 1 0
威佐夫博弈(Wythoff Game):
具体详细证明看转载的博客,在我博客中有,各种常见博弈的解题方法。
1)给你一个局面,让你求是先手输赢。
有了上面的分析,那么这个问题应该不难解决。首先求出差值,差值 * 1.618 == 最小值 的话后手赢,否则先手赢。(注意这里的1.618最好是用上面式子计算出来的,否则精
度要求高的题目会错)
2)给你一个局面,让你求先手输赢,假设先手赢的话输出他第一次的取法。
首先讨论在两边同时取的情况,很明显两边同时取的话,不论怎样取他的差值是不会变的,那么我们可以根据差值计算出其中的小的值,然后加上差值就是大的一个值,当
然能取的条件是求出的最小的值不能大于其中小的一堆的石子数目。
加入在一堆中取的话,可以取任意一堆,那么其差值也是不定的,但是我们可以枚举差值,差值范围是0 --- 大的石子数目,然后根据上面的理论判断满足条件的话就是一种合理的取法。
AC代码:
#include<iostream>
#include<cmath>
using namespace std;
int main()
{int m,n;while(cin>>m>>n){if(m < n){m ^= n;n ^= m;m ^= n;}int k = m - n;if((int)(k * (sqrt(5 * 1.0) + 1) / 2) == n){cout<<"0"<<endl;}else{cout<<"1"<<endl;}}return 0;
}
这篇关于POJ1067 取石子游戏(博弈论)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!