码迷,mamicode.com
首页 > 其他好文 > 详细

博弈基础

时间:2015-08-09 15:34:14      阅读:174      评论:0      收藏:0      [点我收藏+]

标签:

题目链接:

http://acm.hdu.edu.cn/showproblem.php?pid=1944

http://acm.hdu.edu.cn/showproblem.php?pid=1536

技术分享
 1 #include<stdio.h>
 2 #include<cstring>
 3 #include<iostream>
 4 #include<algorithm>
 5 using namespace std;
 6 int s[105];
 7 int f[10005];
 8 int sizeS, T, n, num, sum;
 9 int mex( int t ){
10     bool g[105];
11     memset(g,0,sizeof(g));
12     int tmp;
13     for( int i = 0; i < sizeS; ++i){
14         tmp = t - s[i];
15         if( tmp < 0 )
16             break;
17         if( f[tmp] == -1 )
18             f[tmp] = mex(tmp);
19         g[f[tmp]] = 1;
20     }
21     for( int i = 0; i < 105; ++i)
22         if( g[i] == 0 ){
23             return i;
24         }
25 }
26 int main()
27 {
28     while(~scanf("%d",&sizeS)&&sizeS){
29         for( int i = 0; i < sizeS; ++i){
30             scanf("%d",&s[i]);
31         }//读取数据
32         sort(s,s+sizeS);
33         memset(f,-1,sizeof(f));
34         f[0] = 0;
35         scanf("%d",&T);
36         while(T--){
37             scanf("%d", &n);
38             sum = 0;
39             while(n--){
40                 scanf("%d",&num);
41                 if( f[num] == -1)
42                     f[num] = mex(num);
43                 sum = sum^f[num];
44             }
45             if(!sum)
46                 printf("L");
47             else
48                 printf("W");
49         }
50         printf("\n");
51     }
52 }
View Code

终于明白了SG函数是什么意思,应该算是博弈论入门了吧。。。

关于博弈论的相关资料:

博弈基础知识点:http://blog.csdn.net/acm_cxlove/article/details/7854530

hdoj 1536的题解:http://www.cnblogs.com/AdaByron/archive/2011/08/07/2200981.html

S-G函数的介绍:http://www.cnblogs.com/Knuth/archive/2009/09/05/1561007.html

下面简单小结一下这两天看博弈论的一些知识点:

(一)巴什博奕(Bash Game):只有一堆n个物品,两个人轮流从这堆物品中取物,

规定每次至少取一个,最多取m个。最后取光者得胜。

  令 k = m + 1; 构成一对操作,第一个人无论取多少个,假设为x个,第二个人只需要取 k - x ,选择权又回到了第一个人;

将 n 分解: n = p * ( m + 1 ) + res;  第一个人只要在第一次取res个,剩下的所有回合取 k - x个,必能获胜。

当且仅当 res = 0 的情况下,第二个人才能获胜。

(二)威佐夫博奕(Wythoff Game):有两堆各若干个物品,两个人轮流从某一堆或同时从两堆中取同样多的物品,

规定每次至少取一个,多者不限,最后取光者得胜。

存在一个很好玩的规律,定义(ak, bk)为局势,如果甲面对局势(ak, bk),甲已经输了,则称之为奇异局势,

奇异局势有以下三个性质:

   1、任何自然数都包含在一个且仅有一个奇异局势中。

   2、任意操作都可将奇异局势变为非奇异局势。

   3、采用适当的方法,可以将非奇异局势变为奇异局势。

两个人如果都采用正确操作,那么面对非奇异局势,先拿者必胜;反之,则后拿者取胜。 

ak =[k(1+√5)/2],bk= ak + k  (k=0,1,2,…,n 方括号表示取整函数)

(三)尼姆博奕(Nimm Game):有三堆各若干个物品,两个人轮流从某一堆取任意多的物品,

规定每次至少取一个,多者不限,最后取光者得胜。

  引入了异或运算,奇异局势的异或值为0,非奇异局势的异或值不为0;

  非奇异局势转变为奇异局势,将一个数减少为其他数的奇异和,具体方式可参考1850题。

  hdoj 1850:http://acm.hdu.edu.cn/showproblem.php?pid=1850

技术分享
 1 #include<stdio.h>
 2 #include<string>
 3 int main(){
 4     int N;
 5     int num[105];
 6     int ans;
 7     int cnt;
 8     while(~scanf("%d",&N) && N ){
 9         cnt = ans = 0;
10         for( int i = 0; i < N; ++i){
11             scanf("%d",&num[i]);
12             ans = ans ^ num[i];
13 //            printf("%d\n",ans);
14         }
15         if( ans == 0 )
16             printf("0\n");
17         else{
18             for( int i = 0; i < N; ++i){
19                 int k = num[i]^ans;
20                 if( k < num[i])
21                     cnt++;
22             }
23             printf("%d\n",cnt);
24         }
25     }
26 }
View Code

(四)S-G 函数(Sprague-Garundy)

  首先定义mex ( minimal excludant ) 运算,这是施加于一个集合的运算,表示最小的不属于这个集合的非负整数。

例如mex{0,1,2,4}=3、mex{2,3,5}=0、mex{}=0。

  定义关于图的每个顶点的 Sprague-Garundy 函数 g如下:g(x)=mex{ g(y) | y是x的后继 }

  多棋子的有向图游戏的局面是P-position当且仅当所有棋子所在的位置的SG函数的异或为0。

博弈基础

标签:

原文地址:http://www.cnblogs.com/blueprintf/p/4715088.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!