翻转游戏 II
class Solution {
public:
bool process(string& s){
for(int i=1;i<s.length();++i){
if(s[i]=='+'&&s[i-1]=='+'){
string next=s.substr(0,i-1)+"--"+s.substr(i+1);//后手面对的字符串
if(!process(next)){//如果后手输了,则先手就一定可以赢
return true;
}
}
}
//先手面对字符串s,尝试了所有的情况,发现后手都不会输,那么先手就一定输
return false;
}
bool canWin(string currentState) {
return process(currentState);
}
};
石子游戏
解题思路:
由于所有数的和为奇数,那么我们可以把这些数分成两大类:奇数索引和偶数索引,而且奇数索引的数和与偶数索引的数和一定不相等,而先手可以决定始终拿奇数索引的数或者偶数索引的数,所以先手必胜。
class Solution {
public:
bool stoneGame(vector<int>& piles) {
return true;
}
};
Nim 游戏 (巴什博弈)
解题思路:
n n n 是物品总数 , m m m 是一次最多可以拿的数量 , 0 < = s < = m + 1 0<=s<=m+1 0<=s<=m+1.
巴什博弈:
如果 n = ( m + 1 ) ∗ r + s n=(m+1)*r +s n=(m+1)∗r+s,( r r r 为任意自然数),那么只要先取者率先拿走 s s s 个物品,如果后取者拿走 k ( 1 ≤ k ≤ m ) k(1 ≤ k ≤ m) k(1≤k≤m) 个,那么先取者再拿走 m + 1 − k m+1-k m+1−k 个,以后每次都保持这样的取法,那么先取者肯定获胜。所以,只要保持给对手留下 ( m + 1 ) (m+1) (m+1) 的倍数,就能最后获胜, 但是如果 s = = 0 s==0 s==0 的话,那么先手必定会输。
class Solution {
public:
bool canWinNim(int n) {
return n%4!=0;
}
};
青草游戏
import java.util.Scanner;
public class Main {
public static String process(int n) {
if(n<5) {
if(n==0||n==2)return "后手";
else return "先手";
}
int res=1;
while(res<=n) {
if(process(n-res).equals("后手")) {
return "先手";
}
if(res>n/4)break;
res*=4;
}
return "后手";
}
public static void main(String[] args) {
Scanner scan=new Scanner(System.in);
int n=scan.nextInt();
for(int i=0;i<n;++i) {
if(process(scan.nextInt()%5).equals("先手")) {
System.out.println("niu");
}else {
System.out.println("yang");
}
}
}
}