【题目链接】 http://poj.org/problem?id=3537
【题目大意】
在一个1*n的方格纸上下棋,谁先连三子谁就赢了,问必胜的是谁。
【题解】
我们发现对于一个n规模的游戏。在i位置下棋就能将游戏拆分为i-3和n-i-2两个游戏
对于可拆分的游戏,其sg函数为拆分后游戏sg值的异或和,因此我们用记忆化搜索来记录sg值。
【代码】
#include <cstdio> #include <cstring> using namespace std; int n,sg[2010]; int SG(int n){ if(n<0)return 0; if(sg[n]>=0)return sg[n]; bool tmp[2010]={0}; for(int i=1;i<=n;i++){ int t=SG(i-3)^SG(n-i-2); tmp[t]=1; }for(int i=0;;i++){ if(!tmp[i])return sg[n]=i; } } int main(){ memset(sg,-1,sizeof(sg)); while(~scanf("%d",&n)){ if(SG(n))puts("1"); else puts("2"); }return 0; }