HDU 3951 Coin Game 简单博弈

来源:互联网 发布:客服淘宝退换货流程图 编辑:程序博客网 时间:2024/05/22 03:44

题目大意:

就是现在有N个硬币摆成一个圈, 每次可以取连续的1~K个硬币, 谁取走最后一个就胜利, 注意硬币的位置不变, 也就是说如果1-2-3-4中2被拿走了, 1和3不算连续


大致思路:

其实就是一个简单的分析

首先不难发现如果K = 1, 根据N的奇偶判断即可

如果K >= 2的话, 当N <= K时先手一次拿完, 先手胜

当N > K时, 如果先手一定不能一次拿走全部的硬币, 那么假设先手拿走一定数量后, 剩下的是一个长为L的链, 如果L <= K, 显然后手胜, 如果L > K, 那么由于K >= 2, 所以L >= 3

那么根据L的奇偶性, 后手只需要将这个L拿走中间的1~2个, 剩下的就是一模一样的两个不相邻的链, 于是当先手对其中一条链进行某种操作之后, 后手对于另外一条链进行相同操作

最后一定是后手取完最后的硬币, 后手一定胜利

综上, 当K >= 2时, N <= K先手胜, N > K后手胜


代码如下:

Result  :  Accepted     Memory  :  1576 KB     Time  :  0 ms

/* * Author: Gatevin * Created Time:  2015/5/4 22:34:28 * File Name: Rin_Tohsaka.cpp */#include<iostream>#include<sstream>#include<fstream>#include<vector>#include<list>#include<deque>#include<queue>#include<stack>#include<map>#include<set>#include<bitset>#include<algorithm>#include<cstdio>#include<cstdlib>#include<cstring>#include<cctype>#include<cmath>#include<ctime>#include<iomanip>using namespace std;const double eps(1e-8);typedef long long lint;#define foreach(e, x) for(__typeof(x.begin()) e = x.begin(); e != x.end(); ++e)#define SHOW_MEMORY(x) cout<<sizeof(x)/(1024*1024.)<<"MB"<<endlint T;int N, K;int main(){    scanf("%d", &T);    for(int cas = 1; cas <= T; cas++)    {        scanf("%d %d", &N, &K);        printf("Case %d: ", cas);        if(K == 1)        {            if(N & 1) puts("first");            else puts("second");        }        else        {            if(N <= K) puts("first");            else puts("second");        }    }    return 0;}


0 0