treap 排序二叉树的模板
来源:互联网 发布:ios基于linux还是unix 编辑:程序博客网 时间:2024/06/10 09:09
Description
有一个序列含有一定数量的元素,现在要求写一个程序,满足以下几个要求:【A】支持插入操作(这个序列不允许有重复元素,即是说,如果待插入的元素已经出现在这个序列中,那么请忽略此操作)【B】支持删除操作(如果此序列中不包含待删除的这个元素,则忽略此操作,否则删除这个元素)【C】查找元素x的前继元素(前继元素是指:小于x且与x最接近的元素,当然,如果x已经是序列中的最小元素,则x没有前继元素)【D】查找元素x的后继元素(后继元素是指:大于x且与x最接近的元素,当然,如果x已经是序列中的最大元素,则x没有后继元素)【E】找第K小的元素【F】求某个元素x的秩(即x的排名是多少,从小到大排序)
Input
多组数据(整个文件以输入 -1 结束)对于每组数据,有若干行(最多100000行),表示的意义如下:【A】 insert x 【B】 delete x【C】 predecessor x【D】 successor x【E】 Kth x【F】 rank x这6种操作的意义与上面的定义相对应!【G】 print 表示从小到大输出序列中的所有元素【H】 end表示结束本组数据每组输入数据后有一空行!
Output
对于以上8种操作,分别输出对应信息,如下:【A】 insert x 不用输出任何信息【B】 delete x 如果x存在,则删除x,否则输出 Input Error【C】 predecessor x 如果x不存在,输出 Input Error;否则如果x是序列中的最小元素,输出对应信息(见样例),否则输出x的前继元素【D】 successor x 如果x不存在,输出 Input Error;否则如果x是序列中的最大元素,输出对应信息(见样例),否则输出x的后继元素【E】 Kth x 如果x不合法,输出 Input Error;否则输出第Kth小的元素(见样例)【F】 rank x 如果x不存在,输出 Input Error;否则输出x的排名(见样例)【G】 print 从小到大输出序列中的所有元素,每个元素后加一个逗号,并在最后加上 end of print(见样例)【H】 end输出 end of this test
insert 20insert 5insert 1insert 15insert 9insert 25insert 23insert 30insert 35printKth 0Kth 1Kth 3Kth 5Kth 7Kth 9Kth 10rank 1rank 3rank 5rank 15rank 20rank 30rank 31rank 35successor 15successor 35successor 25successor 26predecessor 1predecessor 20predecessor 23predecessor 15predecessor 111delete 9delete 15delete 25delete 23delete 20printKth 3Kth 4rank 30rank 35end-1
1,5,9,15,20,23,25,30,35,end of printInput ErrorThe 1_th element is 1The 3_th element is 9The 5_th element is 20The 7_th element is 25The 9_th element is 35Input ErrorThe rank of 1 is 1_thInput ErrorThe rank of 5 is 2_thThe rank of 15 is 4_thThe rank of 20 is 5_thThe rank of 30 is 8_thInput ErrorThe rank of 35 is 9_thThe successor of 15 is 2035 is the maximumThe successor of 25 is 30Input Error1 is the minimumThe predecessor of 20 is 15The predecessor of 23 is 20The predecessor of 15 is 9Input Error1,5,30,35,end of printThe 3_th element is 30The 4_th element is 35The rank of 30 is 3_thThe rank of 35 is 4_thend of this test
#include<stdio.h>#include<iostream>#include<string.h>#include<stdlib.h>#include<algorithm>#include<math.h>#include<vector>#include<map>#include<string>using namespace std;#define nn 200005#define inf 0x7ffffstruct treap{ int sz,key,fix,num; treap *ch[2]; treap(int key) { sz=1; num=1; fix=rand(); this->key=key; ch[0]=ch[1]=0; } int compare(int x) const { if(x==key) return -1; return x<key?0:1; } void maintain() { sz=num; if(ch[0]!=0) sz+=ch[0]->sz; if(ch[1]!=0) sz+=ch[1]->sz; }};treap* root;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==0) t=new treap(x); else { int d=x<t->key?0:1; insert(t->ch[d],x); if(t->ch[d]->fix>t->fix) rotate(t,d^1); } t->maintain();}void Delete(treap* &t,int x)//删除{ int d=t->compare(x); if(d==-1) { treap *tmp=t; if(t->ch[0]==0) { t=t->ch[1]; delete tmp; tmp=0; } else if(t->ch[1]==0) { t=t->ch[0]; delete tmp; tmp=0; } else { int k=t->ch[0]->fix>t->ch[1]->fix?1:0; rotate(t,k); Delete(t->ch[k],x); } } else Delete(t->ch[d],x); if(t!=0) t->maintain();}bool Find(treap *t,int x)//查找{ while(t!=0) { int d=t->compare(x); if(d==-1) return true; t=t->ch[d]; } return false;}int kth(treap *t,int k)//找第K小的元素{ if(t==0||k<=0||k>t->sz) return -1; if(t->ch[0]==0&&k==1) return t->key; if(t->ch[0]==0) return kth(t->ch[1],k-1); if(t->ch[0]->sz>=k) return kth(t->ch[0],k); if(t->ch[0]->sz+1==k) return t->key; return kth(t->ch[1],k-1-t->ch[0]->sz);}int Rank(int x) //x的排名是多少,从小到大排序{ int ans=0; treap* p=root; while(1) { if(p->key==x) { ans+=1+(p->ch[0]?p->ch[0]->sz:0); break; } else if(x<p->key) p=p->ch[0]; else { ans+=p->num+(p->ch[0]?p->ch[0]->sz:0); p=p->ch[1]; } } return ans;}int depth(treap *t){ if(t==0) return -1; int l=depth(t->ch[0]); int r=depth(t->ch[1]); return l<r?(r+1):(l+1);}void delettreap(treap* &t)//释放空间{ if(t==0) return; if(t->ch[0]!=0) delettreap(t->ch[0]); if(t->ch[1]!=0) delettreap(t->ch[1]); delete t; t=0;}void Print(treap *t)//打印树,从小到大{ if(t==0) return; Print(t->ch[0]); printf("%d,",t->key); Print(t->ch[1]);}int pre(int x){ treap* p=root; int ans=0; bool fuck=0; while(p) { if(p->key<x) { ans=p->key; fuck=1; } p=p->ch[p->key<x]; } if(fuck) return ans; return inf;}int suc(int x){ treap* p=root; int ans=0; bool fuck=0; while(p) { if(p->key>x) { ans=p->key; fuck=1; } p=p->ch[p->key<=x]; } if(fuck) return ans; return inf;}int main(){ int n,m; char op[30]; while(~scanf("%s",op)) { if(strcmp(op,"-1")==0) break; if(op[0]=='e') { puts("end of this test"); delettreap(root); continue; } if(op[0]=='p'&&op[2]=='i') { Print(root); puts("end of print"); } else { int x; scanf("%d",&x); if(op[0]=='i') { if(!Find(root,x)) insert(root,x); } else if(op[0]=='d') { if(Find(root,x)) Delete(root,x); else printf("Input Error\n"); } else if(op[0]=='p'&&op[2]=='e') { if(Find(root,x)) { int y=pre(x); if(y<inf) printf("The predecessor of %d is %d\n",x,y); else printf("%d is the minimum\n",x); } else printf("Input Error\n"); } else if(op[0]=='s') { if(Find(root,x)) { int y=suc(x); if(y<inf) printf("The successor of %d is %d\n",x,y); else printf("%d is the maximum\n",x); } else printf("Input Error\n"); } else if(op[0]=='K') { int y=kth(root,x); if(y==-1) printf("Input Error\n"); else printf("The %d_th element is %d\n",x,y); } else if(op[0]=='r') { if(!Find(root,x)) printf("Input Error\n"); else printf("The rank of %d is %d_th\n",x,Rank(x)); } } } return 0;}
0 0
- treap 排序二叉树的模板
- 排序二叉树和treap
- Treap--简单的平衡二叉搜索树
- 我的treap模板
- Duan2baka的Treap模板!
- Treap树模板
- [平衡树模板]Treap
- [模板]平衡树treap
- 【模板】Splay二叉树排序
- 白书上的Treap模板
- 大白上的treap模板
- 郁闷的出纳员 treap模板
- 【模板】基于旋转的Treap
- 随机二叉搜索树 Treap
- 二叉排序树,平衡二叉树,Treap平衡树的实现-转帖
- 动态平衡二叉搜索树的简易实现,Treap 树
- C++模板实现的二叉排序(查找)树
- 随机化的二叉搜索树总结(treap,随机输入)
- 深入理解JavaScript系列(32):设计模式之观察者模式
- RAFT algorithm
- FZUOJ 2135 数字游戏
- 配置opencv环境
- Ubuntu系统进程绑定CPU核
- treap 排序二叉树的模板
- 09-散列1. Hashing (25) -- 读题仔细
- 各种排序算法的稳定性和时间复杂度小结
- 常用委托方法
- 深入理解JavaScript系列(33):设计模式之策略模式
- PHP,Mysql-根据一个给定经纬度的点,进行附近地点查询
- Hdu oj 2066 一个人的旅行
- 归档与解归档
- js事件