POJ 2960 S-Nim

本文介绍了一个简单的博弈问题的解决方法,通过计算各个状态的SG值来判断游戏的胜负情况。文章提供了一段C++代码实现,并详细解释了如何通过动态规划获取SG值,最终确定玩家的胜负。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

http://poj.org/problem?id=2960


这个题算是比较简单的博弈了,跟那个只能取fibonacci数博弈一样求没堆石子的sg值,然后看异或之后是否为0,为0是必败态,否则为必胜态


#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>

using namespace std;
const int maxn=10010;

int sg[maxn],s[110],K;
int get_sg(int i)
{
    if(i==0) return 0;
    if(sg[i]!=-1) return sg[i];
    bool vis[maxn]={0};
    for(int j=0;j<K&&s[j]<=i;j++)
        vis[get_sg(i-s[j])]=1;
    for(int j=0;;j++)
     if(!vis[j]) return j;
}
int main()
{
    int n,a,b;
    while(scanf("%d",&K)&&K)
    {
        for(int i=0;i<K;i++)
          scanf("%d",&s[i]);
        sort(s,s+K);
        memset(sg,-1,sizeof(sg));
        for(int i=0;i<=10000;i++)
          sg[i]=get_sg(i);
       /* for(int i=0;i<=12;i++)
          cout<<sg[i]<<" ";
        cout<<endl;*/
        scanf("%d",&n);
        for(int i=0;i<n;i++)
        {
            scanf("%d",&a);
            int ans=0;
            for(int j=0;j<a;j++)
            {
                scanf("%d",&b);
                ans^=sg[b];
            }
            printf(ans==0?"L":"W");
        }
        puts("");
    }
    return 0;
}


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值