• 普通平衡树 Treap


    Code:

    #include<cstdio>
    #include<cstdlib>
    #include<algorithm>
    using namespace std;
    struct Node{
        Node *ch[2];
        int r,v,s,val;
        int cmp(int x) const{
            if(x==v)return -1;
            return x<v?0:1;
        }
        Node(int V){
            s=1,val=1;ch[0]=ch[1]=NULL;
            r=rand();v=V;
        }
        void maintain(){
            s=val;
            if(ch[0]!=NULL)s+=ch[0]->s;
            if(ch[1]!=NULL)s+=ch[1]->s;
        }
    };
    Node *head;
    void rotate(Node* &o,int d){
        Node *k=o->ch[d^1];o->ch[d^1]=k->ch[d];k->ch[d]=o;
        o->maintain();k->maintain();o=k;
    }
    void insert(Node* &o,int x){
        if(o==NULL)o=new Node(x);
        else{
            int d=o->cmp(x);
            if(d==-1){
                ++(o->val);++(o->s);return;
            }
            insert(o->ch[d],x);
            o->maintain();
            if((o->ch[d]->r)>o->r)rotate(o,d^1);
        }
    }
    void erase(Node* &o,int x){
        int d=o->cmp(x);
        if(d==-1){
            if(o->ch[0]==NULL){
                (o->val)--;(o->s)--;
                if(o->val==0)o=o->ch[1];
            }
            else if(o->ch[1]==NULL){
                (o->val)--;(o->s)--;
                if(o->val==0)o=o->ch[0];
            }
            else{
                int d2=(o->ch[0]->r)>(o->ch[1]->r)?1:0;
                rotate(o,d2);
                erase(o->ch[d2],x);
                o->maintain();
            }
        }else {
            erase(o->ch[d],x);
            o->maintain();
        }
    }
    int rank1(Node *o,int x){                  //x的排名
        int d=o->cmp(x);
        int lsize=(o->ch[0]==NULL)?0:o->ch[0]->s;
        if(d==0)return rank1(o->ch[0],x);
        if(d==1)return lsize+o->val+rank1(o->ch[1],x);
        return lsize+1;
    }
    int kth(Node *o,int R){                    //第k大
        int lsize=(o->ch[0]==NULL)?0:o->ch[0]->s;
        if(R<=lsize)return kth(o->ch[0],R);
        if(lsize+o->val>=R)return o->v;
        return kth(o->ch[1],R-lsize-o->val);
    }
    int ans;
    void find1(Node *o,int x){                //前驱
        if(o->v<x){ans=max(ans,o->v);if(o->ch[1]!=NULL)find1(o->ch[1],x);}
        else if(o->ch[0]!=NULL)find1(o->ch[0],x);
    }
    void find2(Node *o,int x){                //后继
        if(o->v>x){ans=min(ans,o->v);if(o->ch[0]!=NULL)find2(o->ch[0],x);}
        else if(o->ch[1]!=NULL)find2(o->ch[1],x);
    }
    int main()
    {
        int n;
        scanf("%d",&n);
        for(int i=1;i<=n;++i)
        {
            int opt,x;
            scanf("%d%d",&opt,&x);
            if(opt==1)insert(head,x);
            if(opt==2)erase(head,x);
            if(opt==3)printf("%d
    ",rank1(head,x));
            if(opt==4)printf("%d
    ",kth(head,x));
            if(opt==5){ans=-10000000;find1(head,x);printf("%d
    ",ans);}
            if(opt==6){ans=10000000;find2(head,x);printf("%d
    ",ans);}
        }
        return 0;
    }
    

      

     
  • 相关阅读:
    jstl 部分标签
    Maven pom.xml 元素配置说明(一)
    spring 参数绑定
    mysql 索引
    ArrayList和HashSet的Contains()方法(转)
    每日记载内容总结44
    剑指offer42:不用加减乘除做加法
    动态规划常见题型
    华为机试-统计每个月兔子的总数
    华为机试-字符串合并处理
  • 原文地址:https://www.cnblogs.com/guangheli/p/9845173.html
Copyright © 2020-2023  润新知