http://acm.hdu.edu.cn/showproblem.php?pid=2897
题意:一堆石子共n个,A、B两人轮流从中取,每次取得石子数必须在[p,q]区间,若剩下的石子数少于p个,则当前取者必须全部取完。最后取完石子的人输。
分析:我看分类的时候他写着是用sg打表找规律。我就照做了。我脑残啊。从一堆中取出物体,不就是巴什博弈吗????
算法分析:
假设先取者为A,后取者为B,初始状态下有石子n个,除最后一次外其他每次取得石子个数必须在[p,q]之间。
- 若当前石子共有n =(p+q)* r个,则A必胜,必胜策略为:A第一次取q个,以后每次若B取K个,A取(p+q-k)个,如此下去最后必剩下p个给B,所以A必胜。
- 若n =(p+q)* r + left个(1< left <= p)B必胜,必胜策略为:每次取石子活动中,若A取k个,则B去(p+q-k)个,那么最后剩下left个给A,此时left <= p,所以A只能一次去完,B胜。
- 若n =(p+q)* r + left个(p < left <= q),则A必胜,必胜策略为:A第一次取t(1< left – t <= p)个,以后每次B取k个,则A取(p+q-k)个,那么最后留下1< left – t <= p给B,则A胜。
-
View Code
// I'm lanjiangzhou //C #include <stdio.h> #include <stdlib.h> #include <string.h> #include <ctype.h> #include <math.h> #include <time.h> //C++ #include <iostream> #include <algorithm> #include <cstdio> #include <cstdlib> #include <cmath> #include <cstring> #include <cctype> #include <stack> #include <string> #include <list> #include <queue> #include <map> #include <vector> #include <deque> #include <set> using namespace std; //*************************OUTPUT************************* #ifdef WIN32 #define INT64 "%I64d" #define UINT64 "%I64u" #else #define INT64 "%lld" #define UINT64 "%llu" #endif //**************************CONSTANT*********************** #define INF 0x3f3f3f3f // aply for the memory of the stack //#pragma comment (linker, "/STACK:1024000000,1024000000") //end int main(){ int n,p,q; while(scanf("%d%d%d",&n,&p,&q)!=EOF){ int s; s=n%(p+q); if(s>0&&s<=p) printf("LOST\n"); else printf("WIN\n"); } return 0; }