[poj 2104][luogu p3834]Kth Number
Posted
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了[poj 2104][luogu p3834]Kth Number相关的知识,希望对你有一定的参考价值。
主席树写一发~
题目大意:
给一个数列,每次询问一个区间内第k小的数.
此题主席树(%Fotile96主席)
代码如下:
1 #include <cstdio> 2 #include <cstring> 3 #include <algorithm> 4 using namespace std; 5 const int N = 200010,M = 12001000; 6 struct tline{int x,idx;bool operator < (const tline &ano) const{return (x < ano.x) || (x == ano.x && idx < ano.idx);}}a[N]; 7 int getint() 8 { 9 int num = 0,s = 1;char ch = getchar();for(;ch < ‘0‘ || ch > ‘9‘;ch = getchar())if(ch == ‘-‘) s = -1; 10 for(;ch >= ‘0‘ && ch <= ‘9‘;ch = getchar()) num = (num << 3) + (num << 1) + ch - ‘0‘; 11 return (s == 1) ? (num) : (-num); 12 } 13 void putint(int x){if(x > 9)putint(x / 10);putchar(x % 10 + ‘0‘);} 14 struct tnode{int lch,rch,sum;}no[M]; 15 int m,n,tcnt = 1,rk[N],root[N]; 16 void insert(int val,int &now,int l,int r) 17 { 18 no[tcnt++] = no[now];now = tcnt - 1;no[now].sum++; 19 if(l == r)return; 20 int mid = (l + r) >> 1; 21 if(val <= mid) insert(val,no[now].lch,l,mid);else insert(val,no[now].rch,mid + 1,r); 22 } 23 int query(int L,int R,int x,int l,int r) 24 { 25 if(l == r)return l; 26 int mid = (l + r) >> 1,tmp = no[no[R].lch].sum - no[no[L].lch].sum; 27 if (tmp >= x) return query(no[L].lch,no[R].lch,x,l,mid); 28 else return query(no[L].rch,no[R].rch,x - tmp,mid + 1,r); 29 } 30 int main() 31 { 32 no[0].lch = no[0].rch = no[0].sum = 0; 33 n = getint();m = getint(); 34 for(int i = 1;i <= n;i++) {a[i].idx = i;a[i].x = getint();} 35 sort(a + 1,a + n + 1); for(int i = 1;i <= n;i++) rk[a[i].idx] = i; 36 root[0] = 0; 37 for(int i = 1;i <= n;i++) {root[i] = root[i - 1];insert(rk[i],root[i],1,n);} 38 for(int i = 1;i <= m;i++) {int l = getint();int r = getint();int val = getint();putint(a[query(root[l - 1],root[r],val,1,n)].x);putchar(‘\\n‘);} 39 return 0; 40 }
不过话说poj一直wa,似乎是空间的锅...
ps.HDU也有:HDU2665
以上是关于[poj 2104][luogu p3834]Kth Number的主要内容,如果未能解决你的问题,请参考以下文章
luogu P3834 模板可持久化线段树 1(主席树)| 静态第k小问题^&