https://www.luogu.org/problemnew/show/P1290
给出n, m,每个人可以用大的数减去任意倍的小的数(大的数被减后>=0),两人轮流操作,遇到一个数为0时即输
#include <bits/stdc++.h>
using namespace std;
typedef long long ll;
bool solve(int n, int m) {
if(!m) return false;
if(n / m == 1) return !solve(m, n % m);
else return true;
}
int main()
{
int t;
scanf("%d", &t);
while(t--) {
int m, n;
scanf("%d%d", &m, &n);
if(m < n) swap(m, n);
if(solve(m, n))
printf("Stan wins\n");
else
printf("Ollie wins\n");
}
}
::n>m
sg(n,m) = mem{sg(n - m, m), sg(n - 2m, m), sg(n - 3m, m), … , sg(m, n % m)};
sg(n - m, m) = mem{sg(n - 2m, m), sg(n - 3m, m), … , sg(m, n % m)}
sg(n - 2m, m) = mem{sg(n - 3m, m), … , sg(m, n % m)}
->除了sg(m, n % m)的项都可以由sg(m, n % m)求出
设sg(m, n % m) = 0, n / m = k, 则sg(n - (k - 1) * m, m) = mem{sg(m, n % m)} = 1
后面的sg就为2, 3, 4, …即为必胜
设sg(m, n % m) = 1, n / m = k, 则sg(n - (k - 1) * m, m) = mem{sg(m, n % m)} = 0
后面的sg也为2, 3, 4, 必胜
可知若n / m == 1, k = 1, sg(n, m) = !sg(m, n % m)