Description:
您需要写一种数据结构(可参考题目标题),来维护一些数,其中需要提供以下操作:
1.插入x数
2.删除x数(若有多个相同的数,因只删除一个)
3.查询x数的排名(排名定义为比当前数小的数的个数+1。若有多个相同的数,因输出最小的排名)
4.查询排名为x的数
5.求x的前驱(前驱定义为小于x,且最大的数)
6.求x的后继(后继定义为大于x,且最小的数)
Code
hzh
#include<bits/stdc++.h>
#define N 200010
using namespace std;
//0:左儿子 1:右儿子
int dad[N], son[2][N], tot[N], V[N];
int rt, cnt, n, opt, x;
void update(int x){
//更新节点总数
tot[x] = tot[son[0][x]] + tot[son[1][x]] + 1;
}
void rotate(int x){
int y = dad[x], z = dad[y];
bool t = son[1][y] == x;//son[t][y] == x
if(z)son[son[1][z] == y][z] = x;
son[t][y] = son[!t][x];
son[!t][x] = y;
dad[x] = z;
dad[y] = x;
dad[son[t][y]] = y;
update(y);
update(x);
}
void splay(int x){
for(; dad[x]; rotate(x))if(dad[dad[x]])
(son[0][dad[x]] == x) ^
(son[0][dad[dad[x]]] == dad[x]) ?
rotate(x) : rotate(dad[x]);
rt = x;
}
void insert(int &x, int y){//把y点插入以x为根的splay
if(!x){
x = y;
return;
}
if(V[y] <= V[x])
insert(son[0][x], y), dad[son[0][x]] = x;
else insert(son[1][x], y), dad[son[1][x]] = x;
update(x);
}
int findkth(int x, int k){//查询以x为根的splay中第k小的数
if(tot[son[0][x]] + 1 == k)
return x;
if(tot[son[0][x]] >= k)
return findkth(son[0][x], k);
return findkth(son[1][x], k - tot[son[0][x]] - 1);
}
int findkless(int x, int k){
//找到比k小的最大的点
if(!x)return 0;
if(V[x] >= k)
return findkless(son[0][x], k);
int t = findkless(son[1][x], k);
if(t)return t;
return x;
}
int findkmore(int x, int k){
//找到比k大的最小的点
if(!x)return 0;
if(V[x] <= k)
return findkmore(son[1][x], k);
int t = findkmore(son[0][x], k);
if(t)return t;
return x;
}
int newpoint(int x){
cnt++;
son[0][cnt] = son[1][cnt] = 0;
dad[cnt] = 0;
V[cnt] = x;
tot[cnt] = 1;
return cnt;
}
void output(){
printf("%d
", rt);
for(int i = 1; i <= cnt; i++)
printf("%d %d %d %d %d
", V[i], dad[i], son[0][i], son[1][i], tot[i]);
puts("");
}
int main(){
scanf("%d", &n);
rt = 0;
while(n--){
scanf("%d%d", &opt, &x);
if(opt == 1){
int t = newpoint(x);
insert(rt, t);
//output();
splay(t);
}
if(opt == 2){
int t = findkmore(rt, x - 1);
splay(t);
dad[son[0][t]] = 0;
dad[son[1][t]] = 0;
int s = son[0][t];
if(!s){
rt = son[1][t];
continue;
}
for(; son[1][s]; s = son[1][s]);
splay(s);
son[1][s] = son[1][t];
dad[son[1][t]] = s;
}
if(opt == 3){
int t = findkmore(rt, x - 1);
splay(t);
printf("%d
", tot[son[0][t]] + 1);
}
if(opt == 4){
int t = findkth(rt, x);
splay(t);
printf("%d
", V[t]);
}
if(opt == 5){
int t = findkless(rt, x);
splay(t);
printf("%d
", V[t]);
}
if(opt == 6){
int t = findkmore(rt, x);
splay(t);
printf("%d
", V[t]);
}
}
}