题目大意:
有一个正整数 n。两名玩家轮流操作。每次操作可以执行以下一种:
将 n 除以一个 n的奇数因子。
将 n 减去 11。
问先手是否有必胜策略。如果先手有必胜策略,输出 Ashishgup,否则输出 FastestFinger。
题目分析:
原则:拿到1的会输掉。
直观分析可以得到:
- 1.当A拿到2或奇数的时候必赢,因为2-1或奇数/奇数都使得对方得到1.
在此基础上继续分析其他数值: 设 p p p为奇质数- 1-1. 如果一个数是 2 ∗ p 2*p 2∗p,那么A只能执行/奇数操作,对方拿到2,对方必赢,因此A必输。
- 1-2. 如果一个数是 2 ∗ p 1 ∗ p 2 ∗ . . . 2*p_1*p_2*... 2∗p1∗p2∗...那么A可以执行/奇数操作,是的对方拿到 2 ∗ p 2*p 2∗p,因此A必赢。
- 2.当A为
2
k
,
k
>
1
2^k,k>1
2k,k>1时候,A只能执行-1操作,因此A必输。
- 2-1.如果 一个数是是
2
k
∗
p
1
∗
p
2
.
.
.
2^k*p_1*p_2...
2k∗p1∗p2...,A执行/奇数操作,对方得到
2
k
2^k
2k,对方必输,因此A必赢。
参考代码:
- 2-1.如果 一个数是是
2
k
∗
p
1
∗
p
2
.
.
.
2^k*p_1*p_2...
2k∗p1∗p2...,A执行/奇数操作,对方得到
2
k
2^k
2k,对方必输,因此A必赢。
//A 必胜态 2,3,奇数... 2*ji^2,2^k*ji
//A 必输 1,4,8。。。2^k(k>1);2*ji
#include <bits/stdc++.h>
using namespace std;
bool Prime(int x) {
for(int i = 2; i * i <= x; i++) {
if(x % i == 0) return false;
}
return true;
}
bool work() {
int x;
cin >> x;
if(x == 1)return 0 ;//0必输态
else if(x==2||x&1) return 1;//2和奇数必赢态
else if(x&2) {//2*奇数
x >>= 1;
if(Prime(x)) return 0;//2*奇质数:必输态
else return 1;//2*奇数*奇数 必赢态
}
else {
while(!(x & 1) )x >>= 1;
if(x == 1) return 0;//2^k,必输态
else return 1;//2^k*ji必赢态。
}
}
int main() {
int t;
cin >> t;
while(t--) {
if(work())cout<<"Ashishgup\n";
else cout<<"FastestFinger\n";
}
}