【平衡树】Treap
2016-05-14 11:40
399 查看
treap=tree+heap;
就是在一颗平衡树上维护一个fix域,使得这棵树如果以key值域看的话是一颗排序树,以fix域看是一个堆。这样利用平均分布的fix值使得这棵树相对平衡。
平衡树里相对好写的就是treap和SBT了,改天膜拜下sbt去。
今天先说treap。
写法
顾名思义就是在平衡树的基础上加了一个堆得维护,(堆都会写吧)
插入删除时记得利用旋转来让孩子的fix值跟父节点的大小关系不变(大根堆小根堆都可以吧)。
好像就没有什么了……..
P.S.
这里的fix是随机数,不是给定的值,给定fix的treap是笛卡尔树。
(md学校评测不让用rand()…..我怎么玩)
废话不多说,上代码…..
我按这个写的,附上原po
就是在一颗平衡树上维护一个fix域,使得这棵树如果以key值域看的话是一颗排序树,以fix域看是一个堆。这样利用平均分布的fix值使得这棵树相对平衡。
平衡树里相对好写的就是treap和SBT了,改天膜拜下sbt去。
今天先说treap。
写法
顾名思义就是在平衡树的基础上加了一个堆得维护,(堆都会写吧)
插入删除时记得利用旋转来让孩子的fix值跟父节点的大小关系不变(大根堆小根堆都可以吧)。
好像就没有什么了……..
P.S.
这里的fix是随机数,不是给定的值,给定fix的treap是笛卡尔树。
(md学校评测不让用rand()…..我怎么玩)
废话不多说,上代码…..
我按这个写的,附上原po
#include <iostream> #include <cstdio> #include <climits> #include <cstdlib> using namespace std; class treap{ public: int key,size,fix; treap* ch[2]; void maintain(){ size=1; if(ch[0]!=NULL) size+=ch[0]->size; if(ch[1]!=NULL) size+=ch[1]->size; } treap(int key){ this->key=key,size=1,fix=rand(),ch[1]=ch[0]=NULL; } int compare(int x){if(key==x) return -1;else return key>x?0:1;} void rotate(treap* &t,int d){ treap *k=t->ch[d^1]; t->ch[d^1]=k->ch[d]; k->ch[d]=t; t->maintain(),k->maintain(); t=k; } void insert(treap* &t,int x){ if(t==NULL) t=new treap(x); else{ int d=x>t->key; insert(t->ch[d],x); if(t->ch[d]->fix>t->fix) rotate(t,d^1); } t->maintain(); } void del(treap* &t,int x){ int d=t->compare(x); if(d==-1){ treap *temp=t; if(t->ch[0]==NULL){ t=t->ch[1]; delete temp; temp=NULL; } else if(t->ch[1]==NULL){ t=t->ch[0]; delete temp; temp=NULL; } else{ int k=t->ch[0]->fix>t->ch[1]->fix?1:0; rotate(t,k); del(t->ch[k],x); } } else del(t->ch[d],x); if(t!=NULL) t->maintain(); } bool find(treap *t,int x){ while(t!=NULL){ int d=t->compare(x); if(d==-1) return 1; t=t->ch[d]; } return 0; } int kth(treap *t,int k){ if(t==NULL||k<=0||k>t->size) return -1; if(t->ch[0]==NULL&&k==1) return t->key; if(t->ch[0]==NULL) return kth(t->ch[1],k-1); if(t->ch[0]->size>=k) return kth(t->ch[0],k); if(t->ch[0]->size+1==k) return t->key; return kth(t->ch[1],k-1-t->ch[0]->size); } int rank(treap *t,int x){ int r; if(t->ch[0]==NULL) r=0; else r=t->ch[0]->size; if(x==t->key) return r+1; if(x<t->key) return rank(t->ch[0],x); return r+1+rank(t->ch[1],x); } void delete_treap(treap* &t){ if(t==NULL) return; if(t->ch[0]!=NULL) delete_treap(t->ch[0]); if(t->ch[1]!=NULL) delete_treap(t->ch[1]); delete t; t=NULL; } };
相关文章推荐
- 数据结构之Treap详解
- Treap(树堆)
- 偷懒专用平衡树——Treap
- Treap(树堆)
- LA5031 Graph and Queries (Treap模版)
- [HNOI2002]营业额统计 (Splay || Treap)
- HYSBZ 1146 网络管理Network Treap+线段树+树链
- 【算法】Treap模板和SBT模板
- SPOJ 3273 Order statistic set
- BZOJ 1588 [HNOI2002]营业额统计
- hdu 4699 Editor 伸展树 treap复习
- Codeforces 375D 数据结构(好题中的好题, 4解)
- bzoj 1503 [NOI2004]郁闷的出纳员 平衡树(treap/Splay)
- 数据结构之Treap
- Treap树学习小结
- NOI2004郁闷的出纳员bzoj3503
- 【水题】统计数字
- bzoj1588营业额统计
- 【Memphis】非旋转Treap及可持久化[Merge,Split]
- Treap学习基本入门