题意就是区间第k大……

题解:

前段时间用主席树搞掉了……

如今看到划分树,是在想来写一遍,结果18号对着学长的代码调了一上午连样例都没过,好桑心……

今天在做NOI2010超级钢琴,忽然发现用划分树很直观,果断决定再战划分树

对着网上的c++代码抄了一遍,A了,可是这编程复杂度有点高,忽然又看见盾哥的代码

很简短,和我原先的代码差不多,他怎么能A了呢……(后来发现区间第k小,我却写的第k大……sb啊)

考虑到盾哥的程序用到了离散化,因此没有考虑存在两个数相等的情况,这样就使代码减少很多

我报着试一试的心态把我认为肯定对的代码随机生成了几组大数据和盾哥的程序对拍,然后就对上了

好的,以后就用盾哥的程序

代码:

c++翻译来的:

 1 var  s,t:array[0..20,0..200000] of longint;
 2      a,rk:array[0..200000] of longint;
 3      i,n,m,x,y,k,j:longint;
 4  procedure sort(l,r:longint);
 5  var i,j,m,temp:longint;
 6  begin
 7  i:=l;j:=r;m:=a[(i+j)>>1];
 8  repeat
 9   while a[i]<m do inc(i);
10   while a[j]>m do dec(j);
11   if i<=j then
12    begin
13    temp:=a[i];a[i]:=a[j];a[j]:=temp;
14    inc(i);dec(j);
15    end;
16  until i>j;
17  if i<r then sort(i,r);
18  if j>l then sort(l,j);
19  end;
20   procedure init;
21    begin
22      readln(n,m);
23      for i:=1 to n do read(a[i]);t[0]:=a;
24      sort(1,n);
25    end;
26  procedure build(h,l,r:longint);
27   var  mid,i,lp,rp,lm:longint;
28   begin
29   mid:=(l+r)>>1;lm:=mid-l+1;lp:=l;rp:=mid+1;
30   for i:=l to mid do
31    if a[i]<a[mid] then dec(lm);
32   for i:=l to r do
33    begin
34    if i=l then s[h,i]:=0 else s[h,i]:=s[h,i-1];
35    if t[h,i]=a[mid] then
36     begin
37     if lm<>0 then
38      begin
39      dec(lm);inc(s[h,i]);t[h+1,lp]:=t[h,i];inc(lp);
40      end
41     else begin t[h+1,rp]:=t[h,i];inc(rp);end;
42     end
43    else
44     if t[h,i]<a[mid] then begin inc(s[h,i]);t[h+1,lp]:=t[h,i];inc(lp);end
45    else begin t[h+1,rp]:=t[h,i];inc(rp);end;
46    end;
47   if l=r then exit;
48   build(h+1,l,mid);
49   build(h+1,mid+1,r);
50   end;
51  function find(h,l,r,x,y,k:longint):longint;
52   var mid,ll,rr:longint;
53   begin
54   if l=r then exit(t[h,l]);
55   mid:=(l+r)>>1;
56   if l=x then ll:=0 else ll:=s[h,x-1];rr:=s[h,y]-ll;
57   if rr>=k then exit(find(h+1,l,mid,l+ll,l+ll+rr-1,k))
58   else exit(find(h+1,mid+1,r,mid+1+x-l-ll,mid+1+y-l-ll-rr,k-rr));
59   end;
60  procedure main;
61   begin
62    build(0,1,n);
63    for i:=1 to m do
64     begin
65      readln(x,y,k);
66      writeln(find(0,1,n,x,y,k));
67     end;
68   end;
69 begin
70   init;
71   main;
72 end.       
View Code

相关文章: