码迷,mamicode.com
首页 > 其他好文 > 详细

HDU 2665

时间:2015-11-08 14:50:08      阅读:175      评论:0      收藏:0      [点我收藏+]

标签:

划分树 求一段区间第K大值

 1 #include<stdio.h>
 2 #include<iostream>
 3 #include<string.h>
 4 #include<algorithm>
 5 using namespace std;
 6 
 7 const int MAXN=100010;
 8 int tree[30][MAXN];
 9 int sorted[MAXN];
10 int toleft[30][MAXN];
11 
12 void build(int l,int r,int root)
13 {
14     if(l==r)return;
15     int mid=(l+r)>>1;
16     int same=mid-l+1;
17     for(int i=l;i<=r;i++)
18       if(tree[root][i]<sorted[mid])
19          same--;
20     int lpos=l;
21     int rpos=mid+1;
22     for(int i=l;i<=r;i++)
23     {
24         if(tree[root][i]<sorted[mid])
25              tree[root+1][lpos++]=tree[root][i];
26         else if(tree[root][i]==sorted[mid]&&same>0)
27         {
28             tree[root+1][lpos++]=tree[root][i];
29             same--;
30         }
31         else
32             tree[root+1][rpos++]=tree[root][i];
33         toleft[root][i]=toleft[root][l-1]+lpos-l;
34 
35     }
36     build(l,mid,root+1);
37     build(mid+1,r,root+1);
38 
39 }
40 
41 
42 int query(int L,int R,int l,int r,int root,int k)
43 {
44     if(l==r)return tree[root][l];
45     int mid=(L+R)>>1;
46     int cnt=toleft[root][r]-toleft[root][l-1];
47     if(cnt>=k)
48     {
49         int newl=L+toleft[root][l-1]-toleft[root][L-1];
50         int newr=newl+cnt-1;
51         return query(L,mid,newl,newr,root+1,k);
52     }
53     else
54     {
55          int newr=r+toleft[root][R]-toleft[root][r];
56          int newl=newr-(r-l-cnt);
57          return query(mid+1,R,newl,newr,root+1,k-cnt);
58     }
59 }
60 
61 
62 int main()
63 {
64     int T;
65     int n,m;
66     int s,t,k;
67     scanf("%d",&T);
68     while(T--)
69     {
70         scanf("%d%d",&n,&m);
71         memset(tree,0,sizeof(tree));
72         for(int i=1;i<=n;i++)
73         {
74             scanf("%d",&tree[0][i]);
75             sorted[i]=tree[0][i];
76         }
77         sort(sorted+1,sorted+n+1);
78         build(1,n,0);
79         while(m--)
80         {
81             scanf("%d%d%d",&s,&t,&k);
82             printf("%d\n",query(1,n,s,t,0,k));
83         }
84     }
85     return 0;
86 }

 

HDU 2665

标签:

原文地址:http://www.cnblogs.com/airot/p/4946933.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!