高僧斗法

题意

n 个物品放在阶梯,向上移动物品,不能越过挡在前面的物品,最后物品都挤在高段台阶,不能移动的输。

题解

两两一组,当移动上面的,可以移动下面的相同距离,所以可以把每组之间的间距看作一堆石子,转化为 Nim 博弈。

代码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
#include <bits/stdc++.h>
#define forl(i, l, r) for (int i = l; i <= r; i++)
#define forr(i, r, l) for (int i = r; i >= l; i--)
#define for1(i, n) for (int i = 1; i <= n; i++)
#define for0(i, n) for (int i = 0; i < n; i++)
#define meminf(a) memset(a, inf, sizeof(a))
#define mem_1(a) memset(a, -1, sizeof(a))
#define mem0(a) memset(a, 0, sizeof(a))
#define inlld(lld) scanf("%lld", &lld)
#define inlf(f) scanf("%lf", &f)
#define ind(d) scanf("%d", &d)
#define ins(s) scanf("%s", s)
#define mp make_pair
#define pb push_back
#define fi first
#define se second
typedef std::pair<long long, long long> pll;
typedef std::vector<long long> vll;
typedef std::pair<int, int> pii;
typedef unsigned long long ull;
typedef std::vector<int> vii;
typedef long double db;
typedef long long ll;
const db pi = acos((db)-1);
const ll inf =0x3f3f3f3f;
const ll mod = 1e9+7;
const int N = 1.1e5;
const db eps = 1e-8;
using namespace std;
int sign(db a) { return a < -eps ? -1 : a > eps; }
int db_cmp(db a, db b){ return sign(a-b); }

vii v,vv;
int main() {
#ifdef PerpEternal
freopen("/Users/perpeternal/Documents/Sketch/data/in.dat", "r", stdin);
// freopen("/Users/perpeternal/Documents/Sketch/data/out.dat", "w", stdout);
#endif
//ios::sync_with_stdio(0); cin.tie(0); cout.tie(0);
int x;
while(~ind(x))v.pb(x);
int Xor=0;
for(int i=0;i+1<v.size();i+=2){
vv.pb(v[i+1]-v[i]-1);
Xor^=vv.back();
}
if(Xor){
for0(i,v.size()-1){
forl(j,v[i]+1,v[i+1]-1){
if(i%2){
if((Xor^vv[i/2])==vv[i/2]+j-v[i]){
printf("%d %d\n",v[i],j);
return 0;
}
}else{
if((Xor^vv[i/2])==vv[i/2]-j+v[i]){
printf("%d %d\n",v[i],j);
return 0;
}
}
}

}
}else puts("-1");
return 0;
}
graph TD
1-->3
2-->3
3-->4
3-->5