hdu 1848 Fibonacci again and again (初写SG函数,详解)
思路:
SG函数的应用,可取的值为不连续的固定值,可用GetSG求出SG,然后三堆数异或。
SG函数相关注释见代码:
相关详细说明请结合前一篇博客:
#include<stdio.h> #include<string.h> #define N 1001 //f[]:可以取走的石子个数 //sg[]:0~n的SG函数值 //hash[]:mex{} int f[N],sg[N],hash[N]; void getSG(int n) { int i,j; memset(sg,0,sizeof(sg)); for(i=1;i<=n;i++) { memset(hash,0,sizeof(hash)); for(j=1;f[j]<=i;j++) //i为石子数,f[j]为可取石子的函数 hash[sg[i-f[j]]]=1; for(j=0;j<=n;j++) //求mes{}中未出现的最小的非负整数 { if(hash[j]==0) { sg[i]=j; break; } } } } int main() { int i,m,n,p; f[0]=f[1]=1; for(i=2;i<=20;i++) f[i]=f[i-1]+f[i-2]; //printf("%d\n",f[20]); getSG(1000); while(scanf("%d%d%d",&m,&n,&p)!=EOF) { if(m==0&&n==0&&p==0) break; if((sg[m]^sg[n]^sg[p])==0) printf("Nacci\n"); else printf("Fibo\n"); } return 0; }