3224: Tyvj 1728 普通平衡树

Time Limit: 10 Sec  Memory Limit: 128 MB
Submit: 5354  Solved: 2196
[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.每个数的数据范围:[-1e7,1e7]

【思路】

Rank tree

Treap实现名次树。需要多维护s,w域分别表示节点数目与相同键值的数目,相应修改maintain,remove和rank操作。

需要注意的是不能单单在insert的时候安排相同结点放在右子,因为有可能结点通过旋转转上来,这就违反了我们的初衷。

【代码】

 #include<cstdio>
#include<ctime>
#include<cstring>
#include<cstdlib>
#include<iostream>
#define FOR(a,b,c) for(int a=(b);a<=(c);a++)
using namespace std; struct Node{
Node* ch[];
int v,r,s,w;
Node(int x):v(x) { ch[]=ch[]=NULL; s=w=; r=rand(); }
void maintain() {
s=w; //change
if(ch[]!=NULL) s+=ch[]->s;
if(ch[]!=NULL) s+=ch[]->s;
}
int cmp(int x) const {
if(x==v) return -; return x<v?:;
}
};
void rotate(Node* &o,int d) {
Node* k=o->ch[d^]; o->ch[d^]=k->ch[d]; k->ch[d]=o;
o->maintain(); k->maintain(); o=k;
}
//不能只是把大于等于x的放在右子树 有可能旋上来
void insert(Node* &o,int x) {
if(o==NULL) o=new Node(x);
else {
int d=o->cmp(x);
if(d==-) { o->w++; o->maintain(); return; } //相同键值的个数
insert(o->ch[d],x);
if(o->ch[d]->r > o->r) rotate(o,d^);
}
o->maintain();
}
void remove(Node* &o,int x){
if(o==NULL) return ;
int d=o->cmp(x);
if(d==-) {
Node* u=o;
if(o->w>) { o->w--; o->maintain(); return ; } //change2
if(o->ch[]!=NULL && o->ch[]!=NULL) {
int d2=o->ch[]->r > o->ch[]->r? :;
rotate(o,d2); remove(o->ch[d2],x);
}
else {
if(o->ch[]!=NULL) o=o->ch[]; else o=o->ch[];
delete u;
}
}
else remove(o->ch[d],x);
if(o!=NULL) o->maintain();
}
int kth(Node* o,int k) {
if(o==NULL || k<= || k>o->s) return ;
int s=o->ch[]==NULL? :o->ch[]->s,w=o->w;
if(s+<=k && k<=s+w) return o->v;
else if(k<=s) return kth(o->ch[],k);
else return kth(o->ch[],k-s-w);
}
int rank(Node* o,int x) {
if(o==NULL) return ;
int d=o->cmp(x),s=o->ch[]==NULL?:o->ch[]->s;
int f= d==? s+o->w:;
if(d==-) return s+;
else return rank(o->ch[d],x)+f;
}
void query1(Node* o,int x,int& ans) {
if(o==NULL) return ;
if(o->v<x) { ans=o->v; query1(o->ch[],x,ans); }
else query1(o->ch[],x,ans);
}
void query2(Node* o,int x,int& ans) {
if(o==NULL) return ;
if(o->v>x) { ans=o->v; query2(o->ch[],x,ans); }
else query2(o->ch[],x,ans);
}
int n,opt,x,ans;
Node* root=NULL; int main() {
//srand(time(0)); //bzoj上不要用 否则RE
scanf("%d",&n);
FOR(i,,n) {
scanf("%d%d",&opt,&x);
switch(opt) {
case : insert(root,x); break;
case : remove(root,x); break;
case : printf("%d\n",rank(root,x)); break;
case : printf("%d\n",kth(root,x)); break;
case : ans=; query1(root,x,ans); printf("%d\n",ans); break;
case : ans=; query2(root,x,ans); printf("%d\n",ans); break;
}
}
return ;
}

bzoj3224 Tyvj 1728 普通平衡树(名次树+处理相同)的更多相关文章

  1. [BZOJ3224]Tyvj 1728 普通平衡树

    [BZOJ3224]Tyvj 1728 普通平衡树 试题描述 您需要写一种数据结构(可参考题目标题),来维护一些数,其中需要提供以下操作:1. 插入x数2. 删除x数(若有多个相同的数,因只删除一个) ...

  2. bzoj3224: Tyvj 1728 普通平衡树(平衡树)

    bzoj3224: Tyvj 1728 普通平衡树(平衡树) 总结 a. cout<<(x=3)<<endl;这句话输出的值是3,那么对应的,在splay操作中,当父亲不为0的 ...

  3. BZOJ 3224 TYVJ 1728 普通平衡树 [Treap树模板]

    3224: Tyvj 1728 普通平衡树 Time Limit: 10 Sec  Memory Limit: 128 MB Submit: 7390  Solved: 3122 [Submit][S ...

  4. bzoj3224: Tyvj 1728 普通平衡树(splay)

    3224: Tyvj 1728 普通平衡树 题目:传送门 题解: 啦啦啦啦又来敲个模版水经验啦~ 代码: #include<cstdio> #include<cstring> ...

  5. 【权值线段树】bzoj3224 Tyvj 1728 普通平衡树

    一个板子. #include<cstdio> #include<algorithm> using namespace std; #define N 100001 struct ...

  6. 替罪羊树—BZOJ3224: Tyvj 1728 普通平衡树

    冬令营被平衡树坑了之后,打算苦练一番数据结构(QAQ). 先是打了一下想学好久的替罪羊树. 替罪羊树实现方法很简单,就是在不满足平衡条件的时候暴力重构子树. 调试小结: 1.删除操作分两类情况:如果某 ...

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

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

  8. 【权值分块】bzoj3224 Tyvj 1728 普通平衡树

    权值分块和权值线段树的思想一致,离散化之后可以代替平衡树的部分功能. 部分操作的时间复杂度: 插入 删除 全局排名 全局K大 前驱 后继 全局最值 按值域删除元素 O(1) O(1) O(sqrt(n ...

  9. 绝对是全网最好的Splay 入门详解——洛谷P3369&BZOJ3224: Tyvj 1728 普通平衡树 包教包会

    平衡树是什么东西想必我就不用说太多了吧. 百度百科: 一个月之前的某天晚上,yuli巨佬为我们初步讲解了Splay,当时接触到了平衡树里的旋转等各种骚操作,感觉非常厉害.而第二天我调Splay的模板竟 ...

随机推荐

  1. Core模块其他常用知识点[OpenCV 笔记14]

    Matx 轻量级的Mat,必须在使用前规定好大小,比如一个2x3的float型的Matx,可以声明为Matx23f Vec Vec是Matx的一个派生类,是一个一维的Matx,跟vector很相似.在 ...

  2. OpenCV(5)-图像掩码操作(卷积)-锐化

    锐化概念 图像平滑过程是去除噪声的过程.图像的主要能量在低频部分,而噪声主要集中在高频部分.图像的边缘信息主要也在高频部分,在平滑处理后,将会丢不部分边缘信息.因此需要使用锐化技术来增强边缘. 平滑处 ...

  3. Java RandomAccessFile的使用(转载的文章,出处http://www.2cto.com/kf/201208/149816.html)

    Java的RandomAccessFile提供对文件的读写功能,与普通的输入输出流不一样的是RamdomAccessFile可以任意的访问文件的任何地方.这就是“Random”的意义所在. Rando ...

  4. Android中Matrix的pre post set方法理解(转载来源:Linux社区 作者:zjmdp)

    虽说以前学习过线性代数和图形学原理,但是在实际中碰到matrix还是疑惑了好一阵子,今天通过向同事请教终于找到一点门路,特总结如下: Matrix主要用于对平面进行缩放,平移,旋转以及倾斜操作,为简化 ...

  5. c++动态绑定与静态绑定

    C++为了支持多态性,采用了动态绑定和静态绑定 相关概念: 对象的静态类型:对象在声明时采用的类型,编译时确定 对象的动态类型:目前所指对象的类型,在运行时确定 class B { } class C ...

  6. ASP.NET数据绑定控件

    数据绑定控件简介 数据绑定分为:数据源 和 数据绑定控件 两部分,数据绑定控件通过数据源来获得数据,通过数据源来隔离数据提供者和数据使用者,数据源有:SqlDataSource,AccessDataS ...

  7. MongoDB笔记(四)基本管理命令

    MongoDB命令帮助系统 基本命令及实例 一基本命令 二基本DDL和DML 三启动与终止 四安全管理 五数据备份恢复与迁移管理 六远程连接管理   MongoDB是一个NoSQL数据库系统:一个数据 ...

  8. 在 lamp(centos)下配置二级 域名 、虚拟主机

    1.你得拥有一个泛域名解析的顶级域名,有一个独立的IP: 2.解析二级域名,如在万网中心里,记录类型为A, 主机记录即为要配的二级域名(如:增加两个:bbs.mydomain.com 和 www.my ...

  9. yii2源码学习笔记(二十)

    Widget类是所有部件的基类.yii2\base\Widget.php <?php /** * @link http://www.yiiframework.com/ * @copyright ...

  10. DISC免费性格测试题

    现在给大家推荐一款世界500强和猎头公司招聘人才时用的DISC性格测评,用在找对象方面也比较合适.大家不妨看下自己的性格,就知道该找什么样的意中人啦--- 在每一个大标题中的四个选择题中只选择一个最符 ...