poj3481 用伸展树来做
2015-05-30 22:59
411 查看
#include <iostream> #include <cstdio> #include <algorithm> #include <cmath> #include <cstring> #include <string.h> #include <queue> //poj3481 伸展树(包括删除的操作) #define N 100010 using namespace std; int pre , key , ch [2], num , root, tot; /* 4、删除最大最小: a)删除最小: 首先执行查找最小的操作。 这时,要删除的节点就在根上。根据二叉查找树的特点,根没有左子节点。 使用根的右子结点作为新的根,删除旧的包含最小值的根。 b)删除最大: 首先执行查找最大的操作。 删除根,并把被删除的根的左子结点作为新的根。 5、删除: 将要删除的节点移至根。 删除根,剩下两个子树L(左子树)和R(右子树)。 使用DeleteMax查找L的最大节点,此时,L的根没有右子树。 使R成为L的根的右子树。 */ void newnode(int &r, int father, int k, int n) { r=++tot; pre[r]=father; ch[father][key[father]<k]=r; key[r]=k; num[r]=n; ch[r][0]=ch[r][1]=0; return ; } void rotate(int x, int kind) //kind为0表示左旋,kind为1表示右旋 { int k=pre[x], g; ch[k][!kind]=ch[x][kind]; pre[ch[x][kind]]=k; ch[x][kind]=k; pre[x]=pre[k]; g=pre[k]; pre[k]=x; if(pre[k]==0) return ; ch[g][key[g]<key[x]]=x; return ; } void Splay(int x, int goal) { int k, g, h; while(pre[x]!=goal) { k=pre[x]; if(pre[k]==goal) { rotate(x, key[k]>key[x]); } else { g=(ch[k][0]==x?0:1); h=(ch[pre[k]][0]==k?0:1); if(g==h) { rotate(k, !g); rotate(x, !g); } else { rotate(x, key[k]>key[x]); rotate(x, key[pre[x]]>key[x]); } } } if(!goal)root=x; return ; } void insert(int k, int n) { int r=root, g, h; if(!r) { newnode(root, 0, k, n); return ; } while(r) { g=r; if(key[r]>k) r=ch[r][0]; else r=ch[r][1]; } newnode(h, g, k, n); Splay(h, 0); return ; } void dele(int x, int kind) //kind为0表示只有左子树,kind为1表示只有右子树 { Splay(x, 0); if(kind) { root=ch[x][1]; pre[root]=0; } else { root=ch[x][0]; pre[root]=0; } return ; } int getleft() { int r=root, k, g; if(!root) return 0; while(r) { k=r; r=ch[r][0]; } g=num[k]; dele(k, 1); return g; } int getright() { int r=root, k, g; if(!root) return 0; while(r) { k=r; r=ch[r][1]; } g=num[k]; dele(k, 0); return g; } int main() { int n, a, b; root=tot=0; while(scanf("%d", &n)&&n) { if(n==1) { scanf("%d%d", &a, &b); insert(b, a); continue; } if(n==2) { printf("%d\n", getright()); } if(n==3) { printf("%d\n", getleft()); } } return 0; }
相关文章推荐
- jackson的循环问题和hibernate懒加载问题
- 更改oracle字符集
- SBT poj3481
- javaweb学习总结(三十一)——国际化(i18n)
- 那些真实
- 飞机大战-子弹的实现
- android Touch事件分发机制
- Android中dispatchTouchEvent, onInterceptTouchEvent, onTouchEvent的理解
- NGUI所见即所得之深入剖析UIPanel,UIWidget,UIDrawCall底层原理
- java并发笔记
- memcached linux安装
- [置顶] Cookie和Session详解
- HNOI2002营业额统计 (伸展树---模板题)
- linux中c语言errno的使用
- 萃取(traits)编程技术的介绍和应用
- 心情
- 那些年我们踩到过的坑(一):为ThreadPoolExecutor 指定RejectedExecutionHandler需要注意的坑
- 网站设置中的各个功能
- 【IPC通信】基于管道的popen和pclose函数
- TF-IDF及其算法