K-th Number POJ - 2104 (主席树模板)

You are working for Macrohard company in data structures department. After failing your previous task about key insertion you were asked to write a new data structure that would be able to return quickly k-th order statistics in the array segment. 
That is, given an array a[1...n] of different integer numbers, your program must answer a series of questions Q(i, j, k) in the form: "What would be the k-th number in a[i...j] segment, if this segment was sorted?" 
For example, consider the array a = (1, 5, 2, 6, 3, 7, 4). Let the question be Q(2, 5, 3). The segment a[2...5] is (5, 2, 6, 3). If we sort this segment, we get (2, 3, 5, 6), the third number is 5, and therefore the answer to the question is 5.

Input

The first line of the input file contains n --- the size of the array, and m --- the number of questions to answer (1 <= n <= 100 000, 1 <= m <= 5 000). 
The second line contains n different integer numbers not exceeding 10 9 by their absolute values --- the array for which the answers should be given. 
The following m lines contain question descriptions, each description consists of three numbers: i, j, and k (1 <= i <= j <= n, 1 <= k <= j - i + 1) and represents the question Q(i, j, k).

Output

For each question output the answer to it --- the k-th number in sorted a[i...j] segment.

Sample Input

7 3
1 5 2 6 3 7 4
2 5 3
4 4 1
1 7 3

Sample Output

5
6
3

Hint

This problem has huge input,so please use c-style input(scanf,printf),or you may got time limit exceed.

给你一数列,q个询问,询问某个区间第k小的数,主席树板子题,

不会主席树的可以戳这里https://blog.csdn.net/Daxian911/article/details/89075748

 

#include <iostream>
#include <cstdio>
#include <cstring>
#include <algorithm>
using namespace std;
const int maxn=1e5+5;
int Rank[maxn],root[maxn],cnt;
struct Tree
{
    int l,r;
    int sum;
    Tree(){
        sum=0;
    }
}tree[maxn*20];
struct node
{
    int x,id;
}Node[maxn];
bool cmp(node a,node b)
{
    return a.x<b.x;
}
void init()
{
    cnt=1;
    root[0]=0;
    tree[0].l=tree[0].r=tree[0].sum=0;
}
void update(int num,int &rt,int l,int r)
{
    tree[cnt++]=tree[rt];
    rt=cnt-1;
    tree[rt].sum++;
    if(l==r)return ;
    int mid=l+r>>1;
    if(num<=mid) update(num,tree[rt].l,l,mid);
    else update(num,tree[rt].r,mid+1,r);
}
int query(int L,int R,int k,int l,int r)
{
    int d=tree[tree[R].l].sum-tree[tree[L].l].sum;
    if(l==r)return l;
    int mid=l+r>>1;
    if(k<=d) return query(tree[L].l,tree[R].l,k,l,mid);
    else return query(tree[L].r,tree[R].r,k-d,mid+1,r);
}
int main()
{
    int n,q;
    scanf("%d%d",&n,&q);
    for(int i=1;i<=n;i++)
        scanf("%d",&Node[i].x),Node[i].id=i;
    sort(Node+1,Node+1+n,cmp);
    for(int i=1;i<=n;i++)
    {
        Rank[Node[i].id]=i;
    }
    init();
    for(int i=1;i<=n;i++)
    {
        root[i]=root[i-1];
        update(Rank[i],root[i],1,n);
    }
    while(q--)
    {
        int l,r,k;
        scanf("%d%d%d",&l,&r,&k);
        printf("%d\n",Node[query(root[l-1],root[r],k,1,n)].x);
    }
    return 0;
}

 

全部评论

相关推荐

不愿透露姓名的神秘牛友
07-09 12:02
ssob上原来真有BOSS啊
硫蛋蛋:这种也是打工的,只不是是给写字楼房东打工
点赞 评论 收藏
分享
屌丝逆袭咸鱼计划:心态摆好,man,晚点找早点找到最后都是为了提升自己好进正职,努力提升自己才是最关键的😤难道说现在找不到找的太晚了就炸了可以鸡鸡了吗😤早实习晚实习不都是为了以后多积累,大四学长有的秋招进的也不妨碍有的春招进,人生就这样
点赞 评论 收藏
分享
nus2201602...:兄弟,你这个简历撕了丢了吧,就是一坨,去找几个项目,理解项目流程,看几遍就是你的了,看看八股就去干了,多看看牛客里别人发出来的简历,对着写,你这写的啥啊,纯一坨
点赞 评论 收藏
分享
码农索隆:卡学历都不行了,开始卡颜值了
点赞 评论 收藏
分享
评论
点赞
收藏
分享

创作者周榜

更多
牛客网
牛客网在线编程
牛客网题解
牛客企业服务