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

POJ 3468 (线段树 区间增减) A Simple Problem with Integers

时间:2015-04-26 18:01:12      阅读:101      评论:0      收藏:0      [点我收藏+]

标签:

这题WA了好久,一直以为是lld和I64d的问题,后来发现是自己的pushdown函数写错了,说到底还是因为自己对线段树理解得不好。

因为是懒惰标记,所以只有在区间分开的时候才会将标记往下传递。更新和查询都要pushdown。

技术分享
 1 #include <cstdio>
 2 
 3 typedef long long LL;
 4 
 5 const int maxn = 100000 + 10;
 6 
 7 int n, m, qL, qR, v;
 8 LL sum[maxn << 2], add[maxn << 2];
 9 
10 inline void maintain(int o)
11 { sum[o] = sum[o*2] + sum[o*2+1]; }
12 
13 void build(int o, int L, int R)
14 {
15     if(L == R) { scanf("%I64d", &sum[o]); return; }
16     int M = (L + R) / 2;
17     build(o*2, L, M);
18     build(o*2+1, M+1, R);
19     maintain(o);
20 }
21 
22 void pushdown(int o, int L, int R)
23 {
24     if(add[o])
25     {
26         int lc = o*2, rc = o*2+1;
27         int M = (L + R) / 2;
28         add[lc] += add[o];
29         add[rc] += add[o];
30         sum[lc] += (LL) add[o] * (M - L + 1);
31         sum[rc] += (LL) add[o] * (R - M);
32         add[o] = 0;
33     }
34 }
35 
36 void update(int o, int L, int R)
37 {
38     if(qL <= L && qR >= R)
39     {
40         add[o] += v;
41         sum[o] += (LL) v * (R - L + 1);
42         return;
43     }
44     int M = (L + R) / 2;
45     pushdown(o, L, R);
46     if(qL <= M) update(o*2, L, M);
47     if(qR > M) update(o*2+1, M+1, R);
48     maintain(o);
49 }
50 
51 LL query(int o, int L, int R)
52 {
53     if(qL <= L && qR >= R) return sum[o];
54     pushdown(o, L, R);
55     int M = (L + R) / 2;
56     LL ans = 0;
57     if(qL <= M) ans += query(o*2, L, M);
58     if(qR > M) ans += query(o*2+1, M+1, R);
59     return ans;
60 }
61 
62 int main()
63 {
64     //freopen("in.txt", "r", stdin);
65 
66     scanf("%d%d", &n, &m);
67     build(1, 1, n);
68     char op[10];
69     while(m--)
70     {
71         scanf("%s", op);
72         if(op[0] == Q)
73         {
74             scanf("%d%d", &qL, &qR);
75             printf("%I64d\n", query(1, 1, n));
76         }
77         else
78         {
79             scanf("%d%d%d", &qL, &qR, &v);
80             update(1, 1, n);
81         }
82     }
83 
84     return 0;
85 }
代码君

 

POJ 3468 (线段树 区间增减) A Simple Problem with Integers

标签:

原文地址:http://www.cnblogs.com/AOQNRMGYXLMV/p/4457945.html

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