poj 2315 Football Game (博弈 nim k game)

来源:互联网 发布:mac装windows虚拟机 编辑:程序博客网 时间:2024/05/23 11:58

题目链接

Description

Alice and Bob both love football very much, and both of them are vanguards. They are both good at football control. One day after a football match, they play an interesting game, in which they shoot footballs forward the goal directly. There are N footballs in front of the goal, and they play this game in turn. For example, if it is Alice’s turn, Alice can choice some footballs (the number of footballs mush equal or less than M) and shoot them forward. Because the footballs’ quality is not very good, footballs are not a complete sphere and can only roll integer times of its girth. And because of restriction of the friction and strength of them, they cannot shoot a football farther then L centimeters. Of course, they know the radius of a football is R centimeters. Alice and Bob love this game very much. If both of them have unlimited IQ and precision shooting skill, can you guess who can win the football game? By the way, though Alice is as strong as Bob, Alice is a girl, so she will shoot first.

Input

The input consists of several cases, each of which contains two lines.

For each test case, the first line contains 4 integers N, M, L and R (1 <= M <= N <= 30, 0 < L < 100000000, 0 < R < 10000), separated by a single space. N is the number of the footballs, M is the maximum number of footballs one player can shot in one turn, L is the maximum distance that a player can shoot, and R is the radius of footballs.

The next line contains N numbers, S(1), S(2), …, S(N) (0 < S(i) < 100000000), which describe the distance between footballs and the goal.

Output

For each case output contains one line describing the name of the winner.

Sample Input

2 1 30 1
8 14
2 1 30 1
8 12
2 1 30 1
8 10
2 1 30 1
40 200

Sample Output

Alice
Bob
Bob
Bob

将这些距离稍微转化一下,就可以看成一个经典的nim游戏,唯一不同的地方就是由只能从一堆中取变成了要从m个堆里取,这种游戏也有一种名称为nimk游戏。
典型的nim游戏是将各石子堆的数量进行异或,结果为0时为必败态,而异或又称为半加运算,只执行加法而不进位,原始的nim游戏为1堆,所以XOR时以二为进位,而现在要执行的堆数为m,即以m+1为进位,我们可以先按照普通加法,将二进制下每个位上的数字加起来,最后将他们分别mod(m+1)即可。

#include<cstdio>#include<cstdlib>#include<cstring>#include <cmath>#include<iostream>#include<algorithm>#define maxn 35#define PI 3.14159265358979323846264338327950288using namespace std;int m,n,l,r;int s[maxn];int XOR[100];int getdis(int k){    return floor(k/(2*PI*r))+1;}int main(){    while(cin>>n>>m>>l>>r)    {        int k =getdis(l);     //每次踢得距离都为周长的整数倍,每次最多能取的石子个数为k-1        for(int i=0;i<n;i++)        {            int p;            cin>>p;            s[i]=getdis(p)%k;   //nim游戏每个石子堆的个数        }        memset(XOR,0,sizeof(XOR));        int maxi=-1;        for(int i=0;i<n;i++)        {            int g=s[i],p=0;            for(int j=0;g;g>>=1,j++)            {                XOR[j]+=g&1;                p++;                maxi=max(maxi,p);            }        }        bool flag =false;        for(int i=0;i<maxi;i++)            if(XOR[i]%(m+1)) flag=true;        if(flag) cout<<"Alice"<<endl;        else cout<<"Bob"<<endl;    }    return 0;}
0 0
原创粉丝点击