题目大意:
给定(n)个棋子,可以选择向左移动若干步,但是不能超过边界或者越过棋子
不能移动者就输了
判断是否先手必赢
博弈论好难啊QAQ
我们考虑用(SG)定理来判定,那么希望分解若干个不相干的游戏
一开始以为是把第(i)个棋子和第(i - 1)个棋子看做一个游戏,然而这做不下去
我们把棋子两两配对,奇数时补充(0)这个棋子
这样的子游戏是独立的并且合法的
移动左棋子,对手可以模仿操作,致使操作无效
因此只需考虑右棋子
就是(Nim)游戏,(SG(x) = x)
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
using namespace std;
#define ri register int
#define rep(io, st, ed) for(ri io = st; io <= ed; io ++)
#define drep(io, ed, st) for(ri io = ed; io >= st; io --)
const int sid = 2e5 + 5;
int a[sid];
int main() {
int T;
scanf("%d", &T);
while(T --) {
int n, x, y, SG = 0;
scanf("%d", &n);
rep(i, 1, n) scanf("%d", &a[i]);
sort(a + 1, a + n + 1);
if(n & 1) SG ^= (a[1] - 1);
for(int j = 1 + (n & 1); j <= n; j += 2)
SG ^= (a[j + 1] - a[j] - 1);
if(SG) printf("Georgia will win
");
else printf("Bob will win
");
}
return 0;
}