Given n piles of stones, two players take turns to operate, each operation can take away one pile of stones, and then put in two piles of smaller stones (the size of the new pile can be 0, and the total number of stones in the two new piles can be greater than the pile of stones taken away), and those who are unable to operate in the end are deemed to have failed.
Ask whether the first player will win if both players adopt the optimal strategy.
input format
The first line contains the integer n.
The second line contains n integers, where the i-th integer represents the number ai of the i-th pile of stones.
output format
If the first player wins, then output Yes
.
Otherwise, output No
.
data range
1≤n,ai≤100
Input sample:
2
2 3
Sample output:
Yes
#include<iostream>
#include<unordered_set>
#include<cstring>
using namespace std;
const int N = 110;
int f[N]; //记录每个状态的sg
int sg(int x)
{
if(f[x]!=-1) return f[x];
unordered_set<int> S;
//列举出每堆石子可以分成哪几种比它小的两堆石子
for(int i=0;i<x;i++){
for(int j=0;j<=i;j++){
//定理:sg(i,j) = sg(i)^sg(j)
S.insert(sg(i)^sg(j));
}
}
for(int i=0;;i++) if(!S.count(i)) return f[x] = i;
}
int main()
{
int n;
cin>>n;
int res = 0;
memset(f,-1,sizeof f);
for(int i=0;i<n;i++)
{
int num;
cin>>num;
res^=sg(num);
}
if(res) cout<<"Yes"<<endl;
else cout<<"No"<<endl;
}