简单博弈10道

hdu1846巴什博弈,n%(m+1)==0先手必败。

#include <iostream>
#include<cstdio>
#include<cstring>
#include<cstdlib>
#include<cmath>
using namespace std;
int main()
{
    int n,a,b;
    scanf("%d",&n);
    while(n--)
    {
        scanf("%d%d",&a,&b);
        if(a%(b+1)==0)
        printf("second\n");
        else printf("first\n");
    }

    return 0;
}

hdu1847

只要留下两类都是2的指数幂,就是必输状态,然后找规律,发现这两类的和为3的倍数。即有下面的结论。

#include <iostream>
#include<cstdio>
#include<cmath>
using namespace std;
int main()
{
   int n;
   while(scanf("%d",&n)!=EOF)
   {
       if(n%3==0)
       printf("Cici\n");
       else printf("Kiki\n");
   }
    return 0;
}

hdu1848

#include <iostream>
#include<cstdio>
#include<cmath>
#include<cstring>
using namespace std;
#define N 1005
int f[N];
int sg[N];
void fun()
{
    int i;
    f[0]=1;
    f[1]=1;
    f[2]=2;
    for(i=3;;i++)
    {
    f[i]=f[i-1]+f[i-2];
    if(f[i]>1000)
    break;
    }
}
int dfs(int v)
{
    int i;
    if(sg[v]!=-1)
    return sg[v];
    bool visit[N]={0};
    for(i=1;i<16;i++)
    {
       if(v>=f[i])
       {
           int temp=dfs(v-f[i]);
           visit[temp]=1;
       }
    }
    for(i=0;visit[i];i++);
    return sg[v]=i;
}
int main()
{
    fun();
    int m,n,p;
    while(scanf("%d%d%d",&m,&n,&p),m||n||p)
    {
        memset(sg,-1,sizeof(sg));
        int ans;
        ans=dfs(m)^dfs(n)^dfs(p);
        if(ans)
        printf("Fibo\n");
        else printf("Nacci\n");
    }
    return 0;
}
hdu1849

裸的NIM博弈,直接异或即可。

#include <iostream>
#include<cstdio>
using namespace std;
int main()
{
    int n,p;
    while(scanf("%d",&n)!=EOF)
    {
        if(n==0)break;
        int ans=0;
        for(int i=0;i<n;i++)
        {
            scanf("%d",&p);
            ans^=p;
        }
        if(ans==0)
        printf("Grass Win!\n");
        else printf("Rabbit Win!\n");
    }
    return 0;
}

hdu1850

简单NIM博弈,如果异或不为0,找出异或可以使其成为0的值, if(num[j]>(ans^num[j]))这是关键。

#include <iostream>
#include<cstdio>
#include<cmath>
#include<cstring>
using namespace std;
int num[105];
int main()
{
    int t;
    while(scanf("%d",&t)&&t)
    {
        int ans=0;
        for(int i=0;i<t;i++)
        {
            scanf("%d",&num[i]);
            ans^=num[i];
        }
        int cnt=0;
        for(int j=0;j<t;j++)
        {
            if(num[j]>(ans^num[j]))
            {
            cnt++;
            }

        }
        printf("%d\n",cnt);
    }

    return 0;
}

hdu1851j简单NIM博弈

#include <iostream>
#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<cstring>
using namespace std;

int main()
{
    int t,n,m,l;
    scanf("%d",&t);
    while(t--)
    {
        scanf("%d",&n);
        int ans=0;
        while(n--)
        {
            scanf("%d%d",&m,&l);
            ans^=(m%(l+1));
        }
        if(ans==0)
        printf("Yes\n");
        else printf("No\n");
    }
    return 0;
}

hdu1907 NIM博弈,全是1的时候,特判,数1的个数,奇数输,偶数赢了。

#include <iostream>
#include<cstdio>
#include<cmath>
#include<cstring>
#include<cstdlib>
using namespace std;

int main()
{
    int t,num;
    scanf("%d",&t);
    while(t--)
    {
        int ans=0,flag=0;
        int p[50];
        scanf("%d",&num);
        for(int i=0; i<num; i++)
        {
            scanf("%d",&p[i]);
            if(p[i]!=1)
                flag=1;
            ans^=p[i];
        }
        if(flag)
        {
            if(ans==0)
                printf("Brother\n");
            else printf("John\n");
        }else
        {
            if(num%2!=0)
                printf("Brother\n");
            else printf("John\n");
        }

    }
    return 0;
}

hdu2147

判断P和N的状态,画出图标即可。利用SG函数的基本性质。P后面的都是N,N后面的一定存在一个P状态。

观察图表规律知道,n和m都是奇数时候,必败。

#include <iostream>
#include<cstdio>
#include<cstring>
#include<cmath>
#include<cstring>
using namespace std;
int main()
{
    int n,m;
    while(scanf("%d%d",&n,&m)!=EOF)
    {
        if(n==0&&m==0)break;
        if(n&1&&m&1)
        printf("What a pity!\n");
        else printf("Wonderful!\n");
    }

    return 0;
}

hdu2148

简单的巴什博弈。

#include <iostream>
#include<cstdio>
#include<cmath>
#include<cstdlib>
#include<cstring>
using namespace std;

int main()
{
    int m,n;
    while(scanf("%d%d",&m,&n)!=EOF)
    {
        if(m%(n+1)==0)
        {
        printf("none\n");
        continue;
        }
        else if(n>m)
        {
            for(int i=m;i<n;i++)
            printf("%d ",i);
            printf("%d\n",n);
        }
        else printf("%d\n",m%(n+1));//这里是开始的时候,如果先出m%(n+1)个,那么剩下的就是必败态了。
    }
    return 0;
}

 

hdu2149 简单的巴什博弈,同上题类似。
#include <iostream>
#include<cstdio>
using namespace std;

int main()
{
    int t,n,m;
    scanf("%d",&t);
    while(t--)
    {
        scanf("%d%d",&n,&m);
        if(m>n)
        printf("Grass\n");
        else if(n%(m+1)==0)
        {
            printf("Rabbit\n");
        }
        else printf("Grass\n");
    }
    return 0;
}

 


  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值