• [模板] 无旋Treap (C++ class)


    注意!本帖不是算法介绍!只是贴代码(逃)

    //嫌stdlib的rand太慢,手打了一个

      1 /*
      2     Author: hotwords
      3 */
      4 
      5 typedef unsigned int tkey;
      6 class Random {
      7     private:
      8         tkey rs1,rs2,rs3;
      9     public:
     10         tkey operator()() {
     11             rs1=(rs1<<9)^(rs2>>6)^rs3;
     12             rs2=(rs2<<8)^(rs3>>7)^rs1;
     13             rs3=(rs1<<7)^(rs2>>8)^rs2;
     14             return rs1^rs2^rs3;
     15         }
     16         void seed(tkey x) {
     17             rs1=x;
     18             rs2=rs1^0x64db3c5e;
     19             rs3=rs1^0xdb7a6f81;
     20         }
     21         Random() {
     22             seed(0x86e241ca);
     23         }
     24 } random;
     25 template<typename tp>
     26 class Treap {
     27     private:
     28         class TNode {
     29             private:
     30                 int p_size,p_csize;
     31             public:
     32                 tp val;int cnt;
     33                 tkey key;
     34                 TNode *lc,*rc;
     35                 TNode(tp v) {
     36                     val=v;p_size=1;
     37                     p_csize=cnt=1;
     38                     key=random();
     39                     lc=rc=0;
     40                 }
     41                 inline int size()const{return this?this->p_size:0;}
     42                 inline int csize()const{return this?this->p_csize:0;}
     43                 void combine() {
     44                     p_size=1+lc->size()+rc->size();
     45                     p_csize=cnt+lc->csize()+rc->csize();
     46                 }
     47                 void split(int k,TNode*& l,TNode*& r) {
     48                     if(!this) {
     49                         l=r=0;return;
     50                     }
     51                     if(k<=lc->size()) {
     52                         lc->split(k,l,r);
     53                         lc=r;r=this;
     54                     } else {
     55                         rc->split(k-lc->size()-1,l,r);
     56                         rc=l;l=this;
     57                     }
     58                     combine();
     59                 }
     60                 tp min() const {
     61                     const TNode *cur=this;
     62                     while(cur->lc) cur=cur->lc;
     63                     return cur->val;
     64                 }
     65                 tp max() const {
     66                     const TNode *cur=this;
     67                     while(cur->rc) cur=cur->rc;
     68                     return cur->val;
     69                 }
     70         } *root;
     71         TNode* merge(TNode* l,TNode* r) {
     72             if(!r) return l;
     73             if(!l) return r;
     74             if(l->key<r->key) {
     75                 l->rc=merge(l->rc,r);
     76                 l->combine();
     77                 return l;
     78             } else {
     79                 r->lc=merge(l,r->lc);
     80                 r->combine();
     81                 return r;
     82             }
     83         }
     84     public:
     85         Treap(){root=0;}
     86         int size()const{return root->size();}
     87         int count()const{return root->csize();}
     88         int rank(tp v) const {
     89             int ans=0;
     90             TNode *cur=root;
     91             while(cur) {
     92                 if(v<cur->val) cur=cur->lc;
     93                 else {
     94                     ans+=cur->lc->csize();
     95                     if(v>cur->val) ans+=cur->cnt,cur=cur->rc;
     96                     else return ans+1;
     97                 }
     98             }
     99             return ans;
    100         }
    101         int nrank(tp v) const {
    102             int ans=0;
    103             TNode *cur=root;
    104             while(cur) {
    105                 if(v<cur->val) cur=cur->lc;
    106                 else ans+=cur->lc->size()+1,cur=cur->rc;
    107             }
    108             return ans;
    109         }
    110         void insert(tp v) {
    111             int k=nrank(v);
    112             TNode *l,*m,*r,*t;
    113             root->split(k,t,r);
    114             t->split(k-1,l,m);
    115             if(m&&m->val==v) ++m->cnt,m->combine();
    116             else m=merge(m,new TNode(v));
    117             root=merge(merge(l,m),r);
    118         }
    119         void erase(tp v) {
    120             int k=nrank(v);
    121             TNode *l,*m,*r,*t;
    122             root->split(k,t,r);
    123             t->split(k-1,l,m);
    124             if(!--m->cnt) {
    125                 delete []m;m=0;
    126             } else m->combine();
    127             root=merge(merge(l,m),r);
    128         }
    129         tp get_kth(int k) const {
    130             TNode *cur=root;
    131             while(cur) {
    132                 if(k<=cur->lc->csize()) cur=cur->lc;
    133                 else {
    134                     k-=cur->lc->csize();
    135                     if(k<=cur->cnt) return cur->val;
    136                     k-=cur->cnt;cur=cur->rc;
    137                 }
    138             }
    139         }
    140         tp prev(tp v) {
    141             int k=nrank(v);
    142             TNode *l,*m,*r,*t;
    143             tp ans;
    144             root->split(k,t,r);
    145             t->split(k-1,l,m);
    146             ans=m->val<v?m->val:l->max();
    147             root=merge(merge(l,m),r);
    148             return ans;
    149         }
    150         tp next(tp v) {
    151             int k=nrank(v);
    152             TNode *l,*r;
    153             tp ans;
    154             root->split(k,l,r);
    155             ans=r->min();
    156             root=merge(l,r);
    157             return ans;
    158         }
    159 };
    [模板] FHQ Treap
  • 相关阅读:
    推荐一个博客,或许给技术流的自己一些启示
    Boost多线程-替换MFC线程
    Python:Matplotlib 画曲线和柱状图(Code)
    AI:机器人与关键技术--总是被科普
    OnLineML一:关于Jubatus 的简介...
    使用PCL::GPU::遇到问题
    dll文件:关于MFC程序不能定位输入点
    实践:使用FLANN.LSH进行检索
    模式识别两种方法:知识和数据
    几个方便编程的C++特性
  • 原文地址:https://www.cnblogs.com/hotwords/p/9043720.html
Copyright © 2020-2023  润新知