HDU 1536 S-Nim (博弈 sg函数 Nim和)

原题网址:

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

思路:

Nim的变形,只是对你每次选取的数量做了限制,但是其他的性质并没有改变,所以可以用sg函数解决;
又或者说,Nim游戏只是一种特例,事实上有多种问题都可以用sg函数解决。

sg函数的定义:

sg(x) = mex { sg(y) | x->y } //mex (minimal excludant)
x->y 表示从x转移到y,mex(Y)表示的是不存在于集合中的最小自然数。例如mex(0,1,2,5,8,9) = 3,mex(1,2,5) = 0
在Nim游戏中可以用sg函数进行分析
(1)一堆石子的情况:
sg(0) = 0,sg(1) =mex{ sg(0)} = 1,sg(2) = mex(sg(0),sg(1)) = 2;。。。
然后总的来说,对于单堆的这种情况,sg(x) = x
(2)多堆石子的情况:
sg(a,b……) = a ^ b ^…… 即 a堆的sg函数值与b堆等的sg函数值的异或。
最后如果是0,说明先手必败,否则先手必胜。

证明:

我不会。
附上我之前看的别人的网址:
http://www.cnblogs.com/exponent/articles/2141477.html
http://www.physixfan.com/archives/563
我觉得这两篇讲的很好,让我对Nim和,sg函数的理解更深了。

AC代码:

#include <iostream>
#include <cstdio>
#include <algorithm>
#include <string.h>

using namespace std;

int s[120];
int sn;

int mem[10010];

int sg(int n){
    if(mem[n] != -1)return mem[n];
    if(n < s[0]) return 0;
    int hash_[102];
    memset(hash_,-1,sizeof(hash_));
    int i = 0;
    for(;n >= s[i] && i < sn;i++){
        hash_[sg(n-s[i])]++;
    }
    for(int j = 0;j < 101;j++){
        if(hash_[j] == -1)
            return mem[n] = j;
    }
    return -200000000;// 这句没啥意思,按照正常的规则走的话根本不会走到这一步。
}

int main()
{

    int ncase;
    int ans;
    while(scanf("%d",&sn),sn){
        memset(mem,-1,sizeof(mem));
        for(int i = 0;i < sn;i++){
            scanf("%d",s+i);
        }
        sort(s,s+sn);
        scanf("%d",&ncase);
        int n;
        int temp;
        for(int i = 1;i <= ncase;i++){
            scanf("%d",&n);
            scanf("%d",&temp);
            ans = sg(temp);
            for(int j = 0;j < n-1;j++){
                scanf("%d",&temp);
                ans ^= sg(temp);
            }
            if(ans != 0)
                printf("W");
            else
                printf("L");
        }
        printf("\n");
    }
    return 0;
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值