3224: Tyvj 1728 普通平衡树

Time Limit: 10 Sec  Memory Limit: 128 MB
Submit: 20328  Solved: 8979
[Submit][Status][Discuss]

Description

您需要写一种数据结构(可参考题目标题),来维护一些数,其中需要提供以下操作:
1. 插入x数
2. 删除x数(若有多个相同的数,因只删除一个)
3. 查询x数的排名(若有多个相同的数,因输出最小的排名)
4. 查询排名为x的数
5. 求x的前驱(前驱定义为小于x,且最大的数)
6. 求x的后继(后继定义为大于x,且最小的数)

Input

第一行为n,表示操作的个数,下面n行每行有两个数opt和x,opt表示操作的序号(1<=opt<=6)

Output

对于操作3,4,5,6每行输出一个数,表示对应答案

Sample Input

10
1 106465
4 1
1 317721
1 460929
1 644985
1 84185
1 89851
6 81968
1 492737
5 493598

Sample Output

106465
84185
492737

HINT

1.n的数据范围:n<=100000
2.每个数的数据范围:[-2e9,2e9]

Source

 

[Submit][Status][Discuss]

刷点模板题。。发现自己treap忘光了。。

没什么好说的,题目里的排名是指从小到大,其余没有什么坑点,那些作为函数哪些作为过程要想清楚。

比无旋treap快,所以说到现在都没有遇上必须用无旋treap的题,除了WC的那道可持久化treap。

 #include<cstdio>
#include<cstdlib>
#include<cstring>
#include<algorithm>
#define rep(i,l,r) for (int i=l; i<=r; i++)
using namespace std; const int N=,inf=;
int n,rt,nd,ans,op,x,ls[N],rs[N],sz[N],h[N],v[N],w[N]; void rrot(int &x){
int y=ls[x]; ls[x]=rs[y]; rs[y]=x;
sz[y]=sz[x]; sz[x]=sz[ls[x]]+sz[rs[x]]+w[x]; x=y;
} void lrot(int &x){
int y=rs[x]; rs[x]=ls[y]; ls[y]=x;
sz[y]=sz[x]; sz[x]=sz[ls[x]]+sz[rs[x]]+w[x]; x=y;
} void ins(int &x,int k){
if (!x){
x=++nd; v[x]=k; h[x]=rand(); sz[x]=w[x]=; return;
}
sz[x]++;
if (v[x]==k) { w[x]++; return; }
if (k<v[x]){ ins(ls[x],k); if (h[ls[x]]<h[x]) rrot(x);}
else { ins(rs[x],k); if (h[rs[x]]<h[x]) lrot(x); }
} void del(int &x,int k){
if (v[x]==k){
if (w[x]>) { w[x]--; sz[x]--; return; }
if (!ls[x] || !rs[x]) { x=ls[x]+rs[x]; return; }
if (h[ls[x]]<h[rs[x]]) rrot(x),del(x,k); else lrot(x),del(x,k);
return;
}
sz[x]--;
if (k<v[x]) del(ls[x],k); else del(rs[x],k);
} int get(int x,int k){
if (!x) return ;
if (v[x]==k) return sz[ls[x]]+;
else if (k<v[x]) return get(ls[x],k); else return sz[ls[x]]+w[x]+get(rs[x],k);
} int find(int x,int k){
if (!x) return ;
if (sz[ls[x]]+<=k && sz[ls[x]]+w[x]>=k) return v[x];
if (sz[ls[x]]>=k) return find(ls[x],k);
else return find(rs[x],k-sz[ls[x]]-w[x]);
} void pre(int x,int k){
if (!x) return;
if (v[x]<k) ans=max(ans,v[x]),pre(rs[x],k); else pre(ls[x],k);
} void nxt(int x,int k){
if (!x) return;
if (v[x]>k) ans=min(ans,v[x]),nxt(ls[x],k); else nxt(rs[x],k);
} int main(){
freopen("bzoj3224.in","r",stdin);
freopen("bzoj3224.out","w",stdout);
for (scanf("%d",&n); n--; ){
scanf("%d%d",&op,&x);
if (op==) ins(rt,x);
if (op==) del(rt,x);
if (op==) printf("%d\n",get(rt,x));
if (op==) printf("%d\n",find(rt,x));
if (op==) ans=,pre(rt,x),printf("%d\n",ans);
if (op==) ans=inf,nxt(rt,x),printf("%d\n",ans);
}
return ;
}

懒得写这么多怎么办,上STL-vector,所有操作都能在库函数里找到。

据说单次操作理论复杂度是线性的,实际上可以看作是根号的,但这里也只慢了一倍而已。

 #include<cstdio>
#include<vector>
#include<algorithm>
#define rep(i,l,r) for (int i=l; i<=r; i++)
using namespace std; const int inf=;
int n,op,x;
vector<int>a; int main(){
scanf("%d",&n); a.reserve();
rep(i,,n){
scanf("%d%d",&op,&x);
if (op==) a.insert(upper_bound(a.begin(),a.end(),x),x);
if (op==) a.erase(lower_bound(a.begin(),a.end(),x));
if (op==) printf("%d\n",int(lower_bound(a.begin(),a.end(),x)-a.begin()+));
if (op==) printf("%d\n",a[x-]);
if (op==) printf("%d\n",*(--lower_bound(a.begin(),a.end(),x)));
if (op==) printf("%d\n",*upper_bound(a.begin(),a.end(),x));
}
return ;
}

[BZOJ3224]普通平衡树(旋转treap,STL-vector)的更多相关文章

  1. BZOJ3224普通平衡树——旋转treap

    题目: 此为平衡树系列第一道:普通平衡树您需要写一种数据结构,来维护一些数,其中需要提供以下操作:1. 插入x数2. 删除x数(若有多个相同的数,因只删除一个)3. 查询x数的排名(若有多个相同的数, ...

  2. BZOJ3224普通平衡树——非旋转treap

    题目: 此为平衡树系列第一道:普通平衡树您需要写一种数据结构,来维护一些数,其中需要提供以下操作:1. 插入x数2. 删除x数(若有多个相同的数,因只删除一个)3. 查询x数的排名(若有多个相同的数, ...

  3. 【bzoj3224】Tyvj 1728 普通平衡树 01Trie姿势+平衡树的四种姿势 :splay,旋转Treap,非旋转Treap,替罪羊树

    直接上代码 正所谓 人傻自带大常数 平衡树的几种姿势:  AVL Red&Black_Tree 码量爆炸,不常用:SBT 出于各种原因,不常用. 常用: Treap 旋转 基于旋转操作和随机数 ...

  4. 平衡树及笛卡尔树讲解(旋转treap,非旋转treap,splay,替罪羊树及可持久化)

    在刷了许多道平衡树的题之后,对平衡树有了较为深入的理解,在这里和大家分享一下,希望对大家学习平衡树能有帮助. 平衡树有好多种,比如treap,splay,红黑树,STL中的set.在这里只介绍几种常用 ...

  5. BZOJ3223文艺平衡树——非旋转treap

    此为平衡树系列第二道:文艺平衡树您需要写一种数据结构,来维护一个有序数列,其中需要提供以下操作: 翻转一个区间,例如原有序序列是5 4 3 2 1,翻转区间是[2,4]的话,结果是5 2 3 4 1 ...

  6. BZOJ3729Gty的游戏——阶梯博弈+巴什博弈+非旋转treap(平衡树动态维护dfs序)

    题目描述 某一天gty在与他的妹子玩游戏.妹子提出一个游戏,给定一棵有根树,每个节点有一些石子,每次可以将不多于L的石子移动到父节点,询问将某个节点的子树中的石子移动到这个节点先手是否有必胜策略.gt ...

  7. BZOJ3224 Tyvj 1728 普通平衡树(Treap)

    本文版权归ljh2000和博客园共有,欢迎转载,但须保留此声明,并给出原文链接,谢谢合作. 本文作者:ljh2000 作者博客:http://www.cnblogs.com/ljh2000-jump/ ...

  8. [bzoj3196][Tyvj1730]二逼平衡树_树套树_位置线段树套非旋转Treap/树状数组套主席树/权值线段树套位置线段树

    二逼平衡树 bzoj-3196 Tyvj-1730 题目大意:请写出一个维护序列的数据结构支持:查询给定权值排名:查询区间k小值:单点修改:查询区间内定值前驱:查询区间内定值后继. 注释:$1\le ...

  9. 4923: [Lydsy1706月赛]K小值查询 平衡树 非旋转Treap

    国际惯例的题面:这种维护排序序列,严格大于的进行操作的题都很套路......我们按照[0,k],(k,2k],(2k,inf)分类讨论一下就好.显然第一个区间的不会变化,第二个区间的会被平移进第一个区 ...

随机推荐

  1. WP8.1 Windows Phone 8.1开发:何如定义Pivot头部样式、定义Pivot头部颜色

    Windows Phone 8.1 ,如何自定义Pivot头部样式?用Pivot控件完成这样的效果. 网上找了好久,只找到了windows phone 8的解决方案. 终于一个大神给支了招,我觉得我有 ...

  2. windows10安装oracle11g报错ORA-01034、ORA-01078

    ORA-01034表示数据库实例未建立,可以先用管理员账号进入一个空白实例 sqlplus / as sysdba; 如果您当前使用的账号是安装oracle的账号,则不需要账号密码就可以登陆oracl ...

  3. recycleView实现item点击更改该item颜色,其它item颜色变回

    项目中需要横向滚动效果,按照以前的思路,我会写一个ScrollView,里边加一个LinearLayout,在代码中动态加入控件,然后动态删除或者改变颜色,现在android有了新控件Recycler ...

  4. nmap导出处理脚本

    import sys log = open("result.gnmap","r") xls = open("output.csv",&quo ...

  5. spin_USACO

    Spinning Wheels1998 ACM NE Regionals Each of five opaque spinning wheels has one or more wedges cut ...

  6. 安装icephp 记

    下面开始安装: 一:yum 安装 首先需要添加一个yum源. # vi /etc/yum.repos.d/zeroc-ice-amzn.repo写入: [zeroc-ice]name=Ice 5 fo ...

  7. 2015多校第7场 HDU 5378 Leader in Tree Land 概率DP

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=5378 题意:一棵n个节点的树.对其节点进行标号(1~n).求恰好存在k个节点的标号是其节点所在子树的最 ...

  8. JS常用操作方法

    1.splice() 方法向/从数组中添加/删除项目,然后返回被删除的项目. 注释:该方法会改变原始数组. 1 <script type="text/javascript"& ...

  9. 查看mysql的版本和端口号

    查看版本:select version(); 查看端口号:show global variables like 'port';

  10. 如何让Footer无论页面长短都在最底部, 并和正文保持固定高度?

    html结构: <div id="container"> <div id="content">页面正文</div> < ...