题意:
一个n*m个格子的棋盘上在(1,m)位置上有一枚棋子,这枚棋子每次可以向下,或向左,或向左下角移动一格,a和b进行移动棋子的游戏,a先移动,最后无法移动的人输,问在两个人都是最优操作的情况下,最后谁会赢。
思路:
为了方便考虑,我们定义棋子先(n,m)移动到(1,1),f[1][1]就是终结点,也就是必败点。最后的答案就是f[n][m],然后根据必胜点和必败点的规则,依次往后递推。
代码:
#include <bits/stdc++.h>
using namespace std;
const int MAXN = 2005;
bool f[MAXN][MAXN];
const int dx[] = {0, -1, -1};
const int dy[] = {-1, -1, 0};
void cal(int x, int y) {
while (x >= 1 && x <= 2000 && y >= 1 && y <= 2000) {
f[x][y] = false;
for (int i = 0; i < 3; i++) {
int nx = x + dx[i], ny = y + dy[i];
if (nx >= 1 && nx <= 2000 && ny >= 1 && ny <= 2000 && !f[nx][ny]) {
f[x][y] = true; break;
}
}
x--; y++;
}
}
int main() {
//freopen("in.txt", "r", stdin);
f[1][1] = false;
for (int i = 2; i <= 2000; i++) cal(i, 1);
for (int j = 2; j <= 2000; j++) cal(2000, j);
int n, m;
while (scanf("%d%d", &n, &m), n || m) {
if (f[n][m]) puts("Wonderful!");
else puts("What a pity!");
}
return 0;
}