马蜂优雅,仅AC on #3 & #13。
#include <bits/stdc++.h>
#include <bits/extc++.h>
// char yyyx[1 << 20], *yx, *xy;
// #define getchar() (yx == xy && (xy = (yx = yyyx) + fread(yyyx, 1, 1 << 20, stdin), yx == xy) ? 0 : *yx++)
template <typename T>
inline void read(T &x)
{
x = 0;
register char c = getchar();
register short f = 1;
while (c < '0' || c > '9')
{
if (c == '-')
f = -1;
c = getchar();
}
while (c >= '0' && c <= '9')
{
x = (x << 1) + (x << 3) + (c ^ 48);
c = getchar();
}
x *= f;
}
template <typename T, typename... Args>
inline void read(T &x, Args &...temps)
{
read(x), read(temps...);
}
using namespace std;
const int N = 1e5 + 5;
const int mod = 998244353;
typedef long long ll;
int n;
struct Treap
{
int rot, tot, son[N][2], val[N], rnd[N], siz[N], cnt[N];
int ert(int x)
{
val[++tot] = x;
rnd[tot] = rand();
siz[tot] = 1;
cnt[tot] = 1;
return tot;
}
void push_up(int p)
{
siz[p] = siz[son[p][0]] + siz[son[p][1]] + cnt[p];
}
void build()
{
rot = ert(-mod);
son[rot][1] = ert(mod);
push_up(rot);
}
void rotate(int &p, bool d)
{
int tmp = son[p][d ^ 1];
son[p][d ^ 1] = son[tmp][d];
son[tmp][d] = p;
p = tmp;
push_up(son[p][d]);
push_up(p);
}
void add(int &p, int x)
{
if (!p)
return p = ert(x), void();
if (x == val[p])
++cnt[p], push_up(p);
else
{
bool d = x > val[p];
add(son[p][d], x);
if (rnd[p] < rnd[son[p][d]])
rotate(p, d ^ 1);
push_up(p);
}
}
void del(int &p, int x)
{
if (!p)
return;
if (x == val[p])
{
if (cnt[p] > 1)
--cnt[p], push_up(p);
else if (son[p][0] || son[p][1])
{
if (!son[p][1] || rnd[son[p][0]] > rnd[son[p][1]])
rotate(p, 1), del(son[p][1], x);
else
rotate(p, 0), del(son[p][0], x);
push_up(p);
}
else
p = 0;
return;
}
if (x < val[p])
del(son[p][0], x);
else
del(son[p][1], x);
push_up(p);
}
int get_rank(int &p, int x)
{
if (!p)
return 1;
if (x == val[p])
return siz[son[p][0]] + 1;
if (x < val[p])
return get_rank(son[p][0], x);
return get_rank(son[p][1], x);
}
int get_val(int &p, int x)
{
if (!p)
return mod;
if (x <= siz[son[p][0]])
return get_val(son[p][0], x);
if (x <= siz[son[p][0]] + cnt[p])
return val[p];
return get_val(son[p][1], x - siz[son[p][0]] - cnt[p]);
}
int get_pre(int x)
{
int p = rot, pre = -1;
while (p)
{
if (val[p] < x)
pre = val[p], p = son[p][1];
else
p = son[p][0];
}
return pre;
}
int get_nxt(int x)
{
int p = rot, nxt = -1;
while (p)
{
if (val[p] > x)
nxt = val[p], p = son[p][0];
else
p = son[p][1];
}
return nxt;
}
} tp;
signed main()
{
read(n);
tp.build();
for (int op, x; n--;)
{
read(op, x);
switch (op)
{
case 1:
tp.add(tp.rot, x);
break;
case 2:
tp.del(tp.rot, x);
break;
case 3:
printf("%d\n", tp.get_rank(tp.rot, x) - 1);
break;
case 4:
printf("%d\n", tp.get_val(tp.rot, x + 1));
break;
case 5:
printf("%d\n", tp.get_pre(x));
break;
case 6:
printf("%d\n", tp.get_nxt(x));
break;
default:
assert(0);
break;
}
}
return 0;
}