记录编号 |
327784 |
评测结果 |
AAAAAAAAAA |
题目名称 |
[河南省队2012] 找第k小的数 |
最终得分 |
100 |
用户昵称 |
AntiLeaf |
是否通过 |
通过 |
代码语言 |
C++ |
运行时间 |
3.304 s |
提交时间 |
2016-10-22 21:39:37 |
内存使用 |
44.90 MiB |
显示代码纯文本
#include<cstdio>
#include<cstring>
#include<algorithm>
using namespace std;
const int maxn=100010;
void build(int,int,int&,int);
int query(int,int,int,int);
int sm[maxn<<5]={0},lc[maxn<<5]={0},rc[maxn<<5]={0},root[maxn<<5]={0},cnt=0;
int n,m,a[maxn],b[maxn],x,l,r,k;
int main(){
#define MINE
#ifdef MINE
freopen("kth.in","r",stdin);
freopen("kth.out","w",stdout);
#endif
scanf("%d%d",&n,&m);
for(int i=1;i<=n;i++)scanf("%d",&a[i]);
copy(a+1,a+n+1,b+1);
sort(b+1,b+n+1);
for(int i=1;i<=n;i++){
x=lower_bound(b+1,b+n+1,a[i])-b;
build(1,n,root[i],root[i-1]);
}
while(m--){
scanf("%d%d%d",&l,&r,&k);
printf("%d\n",query(1,n,root[r],root[l-1]));
}
#ifndef MINE
printf("\n-------------------------DONE-------------------------\n");
for(;;);
#endif
return 0;
}
void build(int l,int r,int &rt,int pr){
sm[rt=++cnt]=sm[pr]+1;
if(l==r)return;
lc[rt]=lc[pr];rc[rt]=rc[pr];
int mid=(l+r)>>1;
if(x<=mid)build(l,mid,lc[rt],lc[pr]);
else build(mid+1,r,rc[rt],rc[pr]);
}
int query(int l,int r,int rt,int pr){
if(l==r)return b[l];
int mid=(l+r)>>1;
if(k<=sm[lc[rt]]-sm[lc[pr]])return query(l,mid,lc[rt],lc[pr]);
else{
k-=sm[lc[rt]]-sm[lc[pr]];
return query(mid+1,r,rc[rt],rc[pr]);
}
}