agc002e
题意:n堆棋子,两个人轮流操作,每次可以从每堆中取出一个或取走最大的一堆。求是否先手必胜。
将石子堆从大到小排序,每次操作相当于从(0,0)开始,向上或向右走一步,走到边界即为获胜。
可证除边界每个左下右上对角线上的状态相同。
#include <bits/stdc++.h>
using namespace std;
const int N=110000;
int n;
int a[N];
int cmp(int x,int y){return x>y;}
int main()
{
//freopen("tt.in","r",stdin);
scanf("%d",&n);
for(int i=1;i<=n;i++)
scanf("%d",&a[i]);
sort(a+1,a+1+n,cmp);
for(int i=1,j;i<=n;i++)
{
if(a[i]==i)
{
for(j=i;j<=n&&a[j]==a[i];j++);j--;
return puts((j-i)&1 ? "First" : "Second"),0;
}
if(a[i]>i&&a[i+1]<i)
return puts((a[i]-i)&1 ? "First" : "Second"),0;
if(a[i]>i&&a[i+1]==i)
{
for(j=i+1;j<=n&&a[j]==a[i+1];j++);j--;
int t=(j-i-1)&(a[i]-i-1);
return puts(t&1 ? "Second" : "First"),0;
}
}
return 0;
}