问题描述
思路
本题就是multiset(二叉线索平衡树)的应用
主要应用两个函数 :lower_bound,upper_bound
看完了有关set 和multiset的CSDN,这题就绝对没问题
- 查询 x 数的排名
排名,说白了就是排序之后的x的下标。
我们只要用lower_bound方法,找到第一个x的位置。
然后从begin开始往后遍历容器,只要达到这个位置,就输出当前下标即可。
2.查询排名为 x 的数
遍历容器,只要当前排名到达x,就输出当前值。
(因为multiset容器无法进行随机访问)
3.求 x 的前驱(前驱定义为小于 x,且最大的数)
前驱,也就是x的前一个。
我们只要用lower_bound方法找到第一个x的位置,然后输出上一个就OK了。
4.求 x 的后继(后继定义为大于 x,且最小的数)。
后继,也就是第一个大于x的数。
我们可以用upper_bound方法,直接找到这个值。
5.插入一个数 x
直接用insert方法插入即可。
代码
#include <iostream>
#include <set>
using namespace std;
int main()
{
int n,op,x,num;
cin>>n;
multiset <int> a;
a.insert(-2147483647);//按题目要求,先插入两个数据,在找前驱和后继的时候找不到就会返回这两个值
a.insert(2147483647);
multiset <int> ::iterator it;
for(int i=0;i<n;i++) {
cin>>op>>x;
if(op==1) {
num=0;
it=a.lower_bound(x);
for(multiset<int>::iterator j=a.begin();j!=a.end();j++) {
if(j!=it) num++;
else break;
}
cout<<num<<endl;
}
else if(op==2) {
num=-1;
for(multiset <int>::iterator j=a.begin();j!=a.end();j++) {
num++;
if(num==x) {
cout<<*j<<endl;
break;
}
}
}
else if(op==3) {
it=a.lower_bound(x);
cout<<*(--it)<<endl;
}
else if(op==4) {
cout<<*(a.upper_bound(x))<<endl;
}
else a.insert(x);
}
return 0;
}