ACM博弈论(入门)

传送门(参考博客):https://www.cnblogs.com/ECJTUACM-873284962/p/6921829.html

一、必胜点和必败点

      必胜点(N)、必败点(P)这里我也非常不理解为什么和英文反着。

     然后我觉得如果单纯解释必胜点和必败点是没有什么意思的,所以我们通过具体的题目看一下:

     hdu 1847 Good Luck in CET-4 Everybody

     

作为计算机学院的学生,Kiki和Cici打牌的时候可没忘记专业,她们打牌的规则是这样的:
1、  总共n张牌;
2、  双方轮流抓牌;
3、  每人每次抓牌的个数只能是2的幂次(即:1,2,4,8,16…)
4、  抓完牌,胜负结果也出来了:最后抓完牌的人为胜者;
假设Kiki和Cici都是足够聪明(其实不用假设,哪有不聪明的学生~),并且每次都是Kiki先抓牌,请问谁能赢呢?
当然,打牌无论谁赢都问题不大,重要的是马上到来的CET-4能有好的状态。

  这里就提供了几个关键信息:

  ①双方轮流抓牌②每人每次抓牌的个数是能是2的幂次(1,2,4,8,16)

  ③规定最后抓完牌的人获胜④规定Kiki先手。

  然后这种题怎么做呢(套路一波)

   其实就是找规律(和打表什么的差不多),

   n = 0  必败点,因为无法进行操作

   n = 1  必胜点,Kiki直接取2的0次幂就可以了,后面的人就没得取了。

  以此类推,我们可以得到以下规律:

   

      n    :   0    1    2    3    4   5    6 ...

position:  P    N   N    P   N   N   P ...

 这样就可以得到规律,如果这个数%3余0,那么就是必败点;否则,它就是必胜点。

 这里提供这道题目的代码:

  

#include<iostream>
#include<cstdio>
using namespace std;
int main()
{
    int n;
    while(cin>>n)
    {
        if(n%3)
        {
            printf("Kiki\n");
        }
        else
        {
            printf("Cici\n");
        }
    }
    return 0;
}

进阶题目: hdu 2147 kiki's game

 这里大家在讨论的时候用了一个很巧妙地办法:

就是根据题意,左下角的那个状态肯定是不能再继续进行下一步操作的状态,那么这个状态就是必败态。

后面完全可以画一个矩阵来进行理解:

  

这样的话就找出规律:如果说行数和列数都是奇数的话,那么这个时候就是必败态;否则就是必胜态

代码:

#include<iostream>
#include<cstdio>
using namespace std;
int main()
{
    int n,m;
    while(cin>>n>>m&&n&&m){

        if(n%2!=0&&m%2!=0){
            printf("What a pity!\n");
        }else{
            printf("Wonderful!\n");
        }
    }
    return 0;
}

明天继续更~~

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值