Problem Description
Alice and Bob are playing a game.
They take turns to operate. There are n numbers, a1 , a2 , ... , an. Every time, the player plays in 3 steps.
1.Arbitrarily chooses one number ai.
2.Arbitrarily chooses another number x(1≤x<ai).
\3. Replace the number ai with gcd(ai,x). Here, gcd(u,v) refers to the Greatest Common Divisor of u and v.
When a player can not make a single move he/she loses the game. Alice moves the first and she asks you to tell her who will win the game if both player play optimally.
Input
The first line contains a number T(1≤T≤100), the number of testcases.
For each testcase, there are two lines.
The first line contains one number n(1≤n≤106).
The second line contains n numbers a1 , a2 , ... , an(1≤ai≤107).
It is guaranteed that for all testcases, ∑n≤106.
Output
For each testcase, output the answer in one line. If Alice will win the game, print "Alice", otherwise print "Bob".
Sample Input
2
1
1
1
2
Sample Output
Bob
Alice
实际上这就是Nim博弈。首先注意到gcd的本质。不妨设\(a = p_1^{x_1}p_2^{x_2}...p_n^{x_n}, b = p_1^{y_1}p_2^{y_2}...p_n^{y_n}\),则\(gcd(x, y) = p_1^{min(x_1, y_1)}p_2^{min(x_2, y_2)}...p_n^{min(x_n, y_n)}\)考虑把每个ai唯一分解为若干个质数幂次的乘积。因为每次x是任意选的,且\(gcd(a_i, x)\)是ai的因子,所以当前玩家可以直接选择当前ai的任意因子,这样很自然的就可以把初始ai的质因子累积个数看做石子数,ai变成1则不能操作等价于此时ai的每个质因子次数为0,也就是石子数为0。用欧拉筛预处理出每个数的质因子个数,对于输入直接查询sg值然后求异或和进行普通nim博弈即可。
#include<bits/stdc++.h>
using namespace std;
const int maxn=1e7+10;
int sg[maxn],primes[maxn];
int m=0;
void getprimes(){
sg[1]=0;
for(int i=2;i<=maxn;i++){
sg[i]=1;
}
for(int i=2;i<=maxn;i++){
if(sg[i]==1) {sg[i]=1;primes[++m]=i;}
for(int j=1;j<=m&&primes[j]*i<=maxn;j++){
sg[primes[j]*i]=sg[i]+1;
if(i%primes[j]==0)break;
}
}
}
int main(){
getprimes();
int T;
cin>>T;
while(T--){
int n,x;
cin>>n;
int ans=0;
int one=0;
for(int i=1;i<=n;i++){
scanf("%d",&x);
if(x==1) one++;
ans^=sg[x];
}
if(one==n) puts("Bob");
else if(ans==0) puts("Bob");
else puts("Alice");
}
return 0;
}