poj 3264 Balanced Lineup

一个简单的线段树,憋了我好久。问题出在了存数据的数组开得不够,因为我建立线段树时要从D-1开始,但是D那一行的元素个数,可能会超过50000所以,存数据的数组要开的大一些。

 1 #include<stdio.h>
 2 #define INF 1000000000
 3 
 4 int n, m,D,a[(50000+1000)<<1],treemin[51000<<2], treemax[51000<<2];
 5 
 6 void build()
 7 {
 8     for(int i = D-1; i > 0; i --)
 9     {
10         if(treemin[i<<1] > n || treemin[i<<1] == 0) a[treemin[i<<1]] = INF;
11         if(treemin[i<<1|1] > n || treemin[i<<1|1] == 0) a[treemin[i<<1|1]] = INF;
12         treemin[i] = (a[treemin[i<<1]]<a[treemin[i<<1|1]] ? treemin[i<<1] : treemin[i<<1|1]);
13         
14         if(treemax[i<<1] > n || treemax[i<<1] == 0) a[treemax[i<<1]] = -1;
15         if(treemax[i<<1|1] > n || treemax[i<<1|1] == 0) a[treemax[i<<1|1]] = -1;
16         treemax[i] = (a[treemax[i<<1]]>a[treemax[i<<1|1]] ? treemax[i<<1] : treemax[i<<1|1]);
17     }    
18 }
19 
20 void querymax(int cur, int x, int y, int s, int t, int& ans1)
21 {
22     int mid = (x + y) >> 1, ls = cur << 1, rs = cur << 1 | 1;
23     if(x >= s && y <= t)
24     {
25         if(a[treemax[cur]] > ans1) ans1 = a[treemax[cur]];
26         return ;
27     }
28     if(mid >= s)
29         querymax(ls, x, mid, s, t, ans1);
30     if(mid + 1 <= t)
31         querymax(rs, mid + 1, y, s, t, ans1);
32 }
33 
34 void querymin(int cur, int x, int y, int s, int t, int& ans2)
35 {
36     int mid = (x + y) >> 1, ls = cur << 1, rs = cur << 1 | 1;
37     if(x >= s && y <= t)
38     {
39         if(ans2 > a[treemin[cur]]) ans2 = a[treemin[cur]];
40         return;
41     }
42     if(mid >= s)
43         querymin(ls, x, mid, s, t, ans2);
44     if(mid+1<= t)
45         querymin(rs, mid+1, y, s, t, ans2);
46 }
47 
48 int solve(int x, int y)
49 {
50     int ans1 = -INF;
51     querymax(1,0,D-1,x,y,ans1);
52     int ans2 = INF;
53     querymin(1,0,D-1,x,y,ans2);
54     //printf("treemax[1]=%d\n",treemax[1]);
55     //printf("ans1 = %d  ans2 = %d\n",ans1, ans2);
56     return ans1 - ans2;
57 }
58 void init()
59 {
60     while(~scanf("%d%d",&n,&m))
61     {
62         for(int i = 1; i <= n; i ++)
63             scanf("%d",&a[i]);
64         for(D = 1; D < n + 2; D <<= 1);
65         for(int i = 0; i < D; i ++)
66         {
67             treemax[D+i] = i;
68             treemin[D+i] = i;
69         }
70         build();
71         int A, B;
72         while(m --)
73         {
74             scanf("%d%d",&A,&B);
75             printf("%d\n",solve(A,B));
76         }
77     }
78 }
79 int main()
80 {
81     init();
82     return 0;
83 }
原文地址:https://www.cnblogs.com/yuzhaoxin/p/2717307.html