提供一种stl新的思路:vector
(当然这是treap,fhq treap的简化版,清清爽爽的短代码,让您远离平衡树和对顶堆)
可采用vector在线,每次边读入GET指令边输出
ADD(x):(插入值为x的数)
使用 insert()和lower_bound(),将某个值插入到它的下界
v.insert(lower_bound(v.begin(),v.end(),某个值),某个值);
GET(i):(输出当前vector里第i大的数)
直接输出v[i-1]因为vector是从0开始存的,v[i-1]即是vector的第i大
附上清爽崽代码:
#include<bits/stdc++.h> using namespace std; #define ll long long #define rep(i,a,b) for(ll i=a;i<=b;++i) #define dwn(i,a,b) for(ll i=a;i>=b;--i) template <typename T> inline void rd(T &x){//读入优化 x=0;char c=getchar();int f=0; while(!isdigit(c)){f|=c=='-';c=getchar();} while(isdigit(c)){x=(x<<1)+(x<<3)+(c^48);c=getchar();} x=f?-x:x; } #define N 200010 int m,n; int a[N]; vector<int>v; int main(){ rd(m),rd(n); rep(i,1,m)rd(a[i]); int l=1,r; rep(i,1,n){ rd(r); rep(j,l,r) v.insert(lower_bound(v.begin(),v.end(),a[j]),a[j]); l=r+1; printf("%d\n",v[i-1]); } return 0; }
补充:vector也能A掉P3369 【模板】普通平衡树
解放生产力,偷懒是人类进步的阶梯
这里附上核心代码
vector<int>v; int n,op,x; int main(){ rd(n); while(n--){ rd(op),rd(x); if(op==1)v.insert(lower_bound(v.begin(),v.end(),x),x); if(op==2)v.erase(lower_bound(v.begin(),v.end(),x)); if(op==3)printf("%d\n",lower_bound(v.begin(),v.end(),x)-v.begin()+1); if(op==4)printf("%d\n",v[x-1]); if(op==5)printf("%d\n",*--lower_bound(v.begin(),v.end(),x)); if(op==6)printf("%d\n",*lower_bound(v.begin(),v.end(),x+1)); } return 0; } /*操作: 1 插入x数 2 删除x数(若有多个相同的数,因只删除一个) 3 查询x数的排名(排名定义为比当前数小的数的个数+1。若有多个相同的数,因输出最小的排名) 4 查询排名为x的数 5 求x的前驱(前驱定义为小于x,且最大的数) 6 求x的后继(后继定义为大于x,且最小的数) */ /* 定义:vector<int>a; 需<vector>头文件 访问元素:a[x] 取出a中的第(x+1)个数(下标从0开始 O(1) a.begin():返回起始元素的迭代器 O(1) a.end():返回终止元素的迭代器 O(1) a.insert(a.begin()+pos,x):在第pos个数后面插入x O(n) a.erase(a.begin()+pos):删除pos位置的数 pos之后的数自动补齐 O(n) lower_bound(a.begin(),a.end(),x)返回第一个==x的位置的迭代器 O(logn) upper_bound(a.begin(),a.end(),x)返回最后一个==x的位置的后面一个的迭代器(x的后继 O(logn) *it:取出迭代器it中的值(大概只有我不知道 */