最简单的巴什模型是:
只有一堆n个物品,两个人轮流从这堆物品中取物,规
定每次至少取一个,最多取m个。最后取光者得胜。
很容易想出策略,如果n%(m+1)==s(s!=0),那么我先取出s个,后面他任意取出1~m中的一个数k,我就取出m+1-k这样保证每一次和为m+1,这样一定是我最后取出。
所以若n%(m+1)==s那么先出的赢,反之若n%(m+1)==0,那么先取得必输.
更普遍的现象是:
有一堆n个物品,两个人轮流从这堆物品中取物,规定每次至少取p个,最多取q个.最后取光者得胜.
n = (m+1)r+s , (r为任意自然数,s≤m), 即n%(p+q) != 0, 则先取者肯定获胜(默认最后一个取的为win)
相应的练习hdu1846,hdu2147,hdu2149
//hdu1846直接套公式 #include <stdio.h> int main() { int T,n,m; scanf("%d",&T); while(T--) { scanf("%d%d",&n,&m); if (n%(m+1)==0)//先手必输 printf("second\n"); else printf("first\n"); } return 0; } //hdu2147有一个游戏,在一个n*m的矩阵中起始位置是(1,m),走到终止位置(n,1);游戏规则是只能向左,向下,左下方向走,想走到终点的为获胜者。 #include <stdio.h> int main() { int n,m; while((scanf("%d%d",&n,&m)==2)&&(n||m)) { if ((n%2==0)||(m%2==0)) printf("Wonderful!\n"); else printf("What a pity!\n"); } return 0; }
//hdu2149公式,注意特殊情况 #include <stdio.h> int main() { int i,n,m; while(scanf("%d%d",&m,&n)==2) { if (m<n) { printf("%d",m); for (i=m+1;i<=n;i++) printf(" %d",i); printf("\n"); } else if (m%(n+1)==0) printf("none\n"); else printf("%d\n",m%(n+1)); } return 0; }