套路拆成 $i\text{ mod }c+j\text{ mod }c$
然后分类讨论,对于 $i+j<c$ 的,显然我们只要记录单向的 $(i,j)$ 即可,没有必要维护双向。
这样做,会导致 $j$ 的最优匹配可能不是 $i$ ,然后这些状态是可以减的,
若 $i>k$ ,则 $(i,j)$ 优于 $(j,k)$ ,则可以把 $(j,k)$ 删去。
#include <cstdio>
#include <cstring>
#include <cmath>
#include <algorithm>
#include <cstdlib>
#include <vector>
#include <map>
#include <queue>
#include <set>
#include <iostream>
#include <ctime>
#include <bitset>
#define gc getchar()
#define ll long long
#define il inline
#define fi first
#define se second
#define mk make_pair
#define pii pair<int, int>
#define pll pair<ll, ll>
#define pb push_back
#define rep(i, a, b) for (int i = a; i <= b; ++i)
#define repn(i, b, a) for (int i = b; i >= a; --i)
#define ite iterator
#define eps 1e-8
using namespace std;
template<class o> il void qr(o &x) {
x = 0; char c = gc; int f = 1;
while (c < '0' || c > '9') {if (c == '-') f = -1; c = gc;}
while (c >= '0' && c <= '9') {x = x * 10 + (c ^ 48); c = gc;}
x *= f;
}
template<class o> void qw(o x) {
if(x / 10) qw(x / 10); putchar(x % 10 + 48);
}
template<class o> void pr1(o x) {
if (x < 0) putchar('-'), x = -x;
qw(x); putchar(' ');
}
template<class o> void pr2(o x) {
if (x < 0) putchar('-'), x = -x;
qw(x); puts("");
}
/* code */
multiset<int> a, b;
int siz, c;
int cal(int x, int op) {
if (!~x) return -1;
multiset<int>::ite it = a.upper_bound(c - 1 - x);
if (it == a.begin()) return -1; --it;
if (op == 1 && *it == x && a.count(x) == 1) return (it == a.begin()) ? -1 : *(--it);
return *it;
}
void ins(int x) {
++siz;
if (siz == 1) {a.insert(x); return ;}
int y = cal(x, 0), z = cal(y, 1), w = cal(z, 1);
if ((~y) && z < x) {
if (z != -1 && y == w) b.erase(b.find(z + y));
b.insert(x + y);
} a.insert(x);
}
void del(int x) {
--siz; a.erase(a.find(x));
if (!siz) return;
int y = cal(x, 0), z = cal(y, 1), w = cal(z, 1);
if ((~y) && z < x) {
if (z != -1 && y == w) b.insert(y + z);
b.erase(b.find(x + y));
}
}
int query() {
multiset<int>::ite it = a.end(); --it;
if (a.count(*it) > 1) return 2 * (*it) % c;
int w = *it; --it; w += *it;
return w % c;
}
void solve() {
int n; qr(n); qr(c);
int las = 0;
rep (i, 1, n) {
int op, x; qr(op), qr(x); x ^= las;
if (op == 1) ins(x % c);
else del(x % c);
if (siz <= 1) puts("EE"), las = 0;
else pr2(las = max(query(), b.empty() ? 0 : *--b.end()));
}
}
int main() {
//int T; qr(T); while (T--) {
solve();
//}
return 0;
}
最后一次更新于2021-01-08
0 条评论