|
输出的顺序错了,不知道为什么
- #include<bits/stdc++.h>
- using namespace std;
- const int SIZE=1e6+9;
- const int inf=1<<30;
- struct Treap{int l,r,val,dat,cnt,size;}a[SIZE];
- int tot,root,n;
- inline int New(int val){
- a[++tot].val=val;
- a[tot].dat=rand();
- a[tot].cnt=a[tot].size=1;
- return tot;
- }
- inline void Update(int p){
- a[p].size=a[a[p].l].size+a[a[p].r].size+a[p].cnt;
- }
- inline void Build(){
- New(-inf),New(inf);
- root=1,a[1].r=2;
- Update(root);
- }
- inline void zig(int &p){
- int q=a[p].l;
- a[p].l=a[q].r,a[q].r=p,p=q;
- Update(a[p].r),Update(p);
- }
- inline void zag(int &p){
- int q=a[p].r;
- a[p].r=a[q].l,a[q].l=p,p=q;
- Update(a[p].l),Update(p);
- }
- void Insert(int &p,int val){
- if(p==0) return p=New(val),void();
- if(val==a[p].val) return a[p].cnt++,Update(p),void();
- if(val<a[p].val){
- Insert(a[p].l,val);
- if(a[p].dat<a[a[p].l].dat) zig(p);
- }
- else{
- Insert(a[p].r,val);
- if(a[p].dat<a[a[p].r].dat) zag(p);
- }
- Update(p);
- }
- inline int GetPre(int val){
- int ans=1;
- int p=root;
- while(p){
- if(val==a[p].val){
- if(a[p].l>0){
- p=a[p].l;
- while(a[p].r>0) p=a[p].r;
- ans=p;
- }
- break;
- }
- if(a[p].val<val&&a[p].val>a[ans].val) ans=p;
- p=(val<a[p].val)?a[p].l:a[p].r;
- }
- return a[ans].val;
- }
- inline int GetNext(int val){
- int ans=2;
- int p=root;
- while(p){
- if(val==a[p].val){
- if(a[p].r>0){
- p=a[p].r;
- while(a[p].l>0) p=a[p].l;
- ans=p;
- }
- break;
- }
- if(a[p].val>val&&a[p].val<a[ans].val) ans=p;
- p=(val<a[p].val)?a[p].l:a[p].r;
- }
- return a[ans].val;
- }
- int GetRankByVal(int p,int val){
- if(p==0) return 0;
- if(val==a[p].val) return a[a[p].l].size+1;
- if(val<a[p].val) return GetRankByVal(a[p].l,val);
- return GetRankByVal(a[p].r,val)+a[a[p].l].size+a[p].cnt;
- }
- int GetValByRank(int p,int rank){
- if(p==0) return inf;
- if(a[a[p].l].size>=rank) return GetValByRank(a[p].l,rank);
- if(a[a[p].l].size+a[p].cnt>=rank) return a[p].val;
- return GetValByRank(a[p].r,rank-a[a[p].l].size-a[p].cnt);
- }
- void Remove(int &p,int val){
- if(p==0) return;
- if(val==a[p].val){
- if(a[p].cnt>1){
- a[p].cnt--,Update(p);
- return;
- }
- if(a[p].l||a[p].r){
- if(a[p].r==0||a[a[p].l].dat>a[a[p].r].dat) zig(p),Remove(a[p].r,val);
- else zag(p),Remove(a[p].l,val);
- Update(p);
- }
- else p=0;
- return;
- }
- (val<a[p].val)?Remove(a[p].l,val):Remove(a[p].r,val);
- Update(p);
- }
- void middle_traval(int x){
- if(x<=0||x>1500000000) return;
- cout<<a[x].val<<" "<<a[x].cnt<<'\n';
- middle_traval(a[x].l);
- middle_traval(a[x].r);
- }
- int main(){
- srand((unsigned)time(NULL));
- ios::sync_with_stdio(0);
- Build();
- cin>>n;
- for(int i=1;i<=n;++i){
- int x;
- cin>>x;
- Insert(root,x);
- }
- Remove(root,-inf),Remove(root,inf);
- middle_traval(root);
- // while(n--){
- // int opt,x;
- // cin>>opt>>x;
- // if(opt==1) Insert(root,x);
- // else if(opt==2) Remove(root,x);
- // else if(opt==3) cout<<GetRankByVal(root,x)-1<<'\n';
- // else if(opt==4) cout<<GetValByRank(root,x+1)<<'\n';
- // else if(opt==5) cout<<GetPre(x)<<'\n';
- // else if(opt==6) cout<<GetNext(x)<<'\n';
- // }
- return 0;
- }
复制代码 |
|