Treap平衡树,模板题,无题解。
Code:
#include<bits/stdc++.h>
#define rep(i,j,k) for(int i=j;i<=k;i++)
using namespace std;
template<typename T> void read(T &num){
char c=getchar();num=0;T f=1;
while(c<'0'||c>'9'){if(c=='-')f=-1;c=getchar();}
while(c>='0'&&c<='9'){num=(num<<3)+(num<<1)+(c^48);c=getchar();}
num*=f;
}
template<typename T> void qwq(T x){
if(x>9)qwq(x/10);
putchar(x%10+'0');
}
template<typename T> void write(T x){
if(x<0){x=-x;putchar('-');}
qwq(x);putchar('\n');
}
struct wzy{
int ls,rs,val,pri,cnt,siz;
}tree[100010];
int tot=0;int root=0;
inline void Zig(int &pos){//you
int temp=tree[pos].ls;
tree[pos].ls=tree[temp].rs;tree[temp].rs=pos;
tree[temp].siz=tree[pos].siz;
tree[pos].siz=tree[tree[pos].ls].siz+tree[tree[pos].rs].siz+tree[pos].cnt;
pos=temp;return;
}
inline void Zag(int &pos){//zuo
int temp=tree[pos].rs;
tree[pos].rs=tree[temp].ls;tree[temp].ls=pos;
tree[temp].siz=tree[pos].siz;
tree[pos].siz=tree[tree[pos].ls].siz+tree[tree[pos].rs].siz+tree[pos].cnt;
pos=temp;return;
}
inline void Change(int &pos,int w){
if(!pos){
pos=++tot;tree[pos].val=w;tree[pos].pri=rand();
tree[pos].cnt=tree[pos].siz=1;tree[pos].ls=tree[pos].rs=0;return;
}else{tree[pos].siz++;}
if(tree[pos].val==w){tree[pos].cnt++;}
else if(tree[pos].val>w){
Change(tree[pos].ls,w);
if(tree[tree[pos].ls].pri<tree[pos].pri)Zig(pos);
}else{
Change(tree[pos].rs,w);
if(tree[tree[pos].rs].pri<tree[pos].pri)Zag(pos);
}
return;
}
inline void Del(int &pos,int w){
if(tree[pos].val==w){
if(tree[pos].cnt>1){tree[pos].cnt--;tree[pos].siz--;return;}
if(!tree[pos].ls||!tree[pos].rs){pos=tree[pos].ls+tree[pos].rs;}
else if(tree[tree[pos].ls].pri<tree[tree[pos].rs].pri){Zig(pos);Del(pos,w);}
else{Zag(pos);Del(pos,w);}
return;
}
tree[pos].siz--;
if(w<tree[pos].val){Del(tree[pos].ls,w);}
else{Del(tree[pos].rs,w);}
return;
}
inline int Quernk(int w){
int x=root;int ret=0;
while(x){
if(tree[x].val==w){return (ret+tree[tree[x].ls].siz+1);}
else if(tree[x].val>w){x=tree[x].ls;}
else{ret+=tree[tree[x].ls].siz+tree[x].cnt;x=tree[x].rs;}
}
return ret;
}
inline int Quekth(int k){
int x=root;
while(x){
if(tree[tree[x].ls].siz+1<=k&&k<=tree[tree[x].ls].siz+tree[x].cnt){return tree[x].val;}
else if(k<tree[tree[x].ls].siz+1){x=tree[x].ls;}
else{k-=tree[tree[x].ls].siz+tree[x].cnt;x=tree[x].rs;}
}
return 0;
}
inline int Quepre(int w){
int x=root;int ret=-INT_MAX;
while(x){
if(tree[x].val<w){ret=tree[x].val;x=tree[x].rs;}
else{x=tree[x].ls;}
}
return ret;
}
inline int Quesuf(int w){
int x=root;int ret=INT_MAX;
while(x){
if(tree[x].val>w){ret=tree[x].val;x=tree[x].ls;}
else{x=tree[x].rs;}
}
return ret;
}
int main(){
srand(time(NULL));
int n;read(n);
rep(i,1,n){
int opt,x;read(opt);read(x);
if(opt==1){
Change(root,x);
}else if(opt==2){
Del(root,x);
}else if(opt==3){
write(Quernk(x));
}else if(opt==4){
write(Quekth(x));
}else if(opt==5){
write(Quepre(x));
}else{
write(Quesuf(x));
}
}
return 0;
}