https://vjudge.net/problem/POJ-3468
线段树区间更新(lazy数组)模板题
1 #include<iostream> 2 #include<cstdio> 3 #include<queue> 4 #include<cstring> 5 #include<algorithm> 6 #include<cmath> 7 #include<map> 8 #define lson l, m, rt<<1 9 #define rson m+1, r, rt<<1|1 10 #define INF 0x3f3f3f3f 11 typedef long long ll; 12 using namespace std; 13 ll sum[100010<<2], lazy[100010<<2]; 14 void PushUP(int rt) 15 { 16 sum[rt] = sum[rt<<1]+sum[rt<<1|1]; 17 } 18 void PushDown(int rt, int m) 19 { 20 if(lazy[rt]){//若有标记下移 21 lazy[rt<<1] += lazy[rt]; 22 lazy[rt<<1|1] += lazy[rt]; 23 sum[rt<<1] += (m-(m>>1))*lazy[rt]; 24 sum[rt<<1|1] += (m>>1)*lazy[rt]; 25 lazy[rt] = 0;//取消本层标记 26 } 27 } 28 void build(int l, int r, int rt) 29 { 30 lazy[rt] = 0;//一定写在if外初始化 31 if(l == r){ 32 scanf("%lld", &sum[rt]); 33 return ; 34 } 35 int m = (l+r)>>1; 36 build(lson); 37 build(rson); 38 PushUP(rt); 39 } 40 ll Query(int L, int R, int l, int r, int rt) 41 { 42 if(L<=l&&R>=r){ 43 return sum[rt]; 44 } 45 PushDown(rt, r-l+1);//向下更新 46 int m = (l+r)>>1; 47 ll ans=0; 48 if(L <= m) ans += Query(L, R, lson); 49 if(R > m) ans += Query(L, R, rson); 50 return ans; 51 } 52 void Update(int L, int R, ll add, int l, int r, int rt) 53 { 54 if(L<=l&&R>=r){ 55 sum[rt] += (r-l+1)*add; 56 lazy[rt] += add; 57 return ; 58 } 59 PushDown(rt, r-l+1);//向下而更新 60 int m=(l+r)>>1; 61 if(L <= m) Update(L, R, add, lson); 62 if(R > m) Update(L, R, add, rson); 63 PushUP(rt); 64 } 65 int main() 66 { 67 int n, m, a, b; 68 ll c; 69 char op[3]; 70 scanf("%d%d", &n, &m); 71 build(1, n, 1); 72 for(int i = 0; i < m; i++){ 73 scanf("%s", &op); 74 if(op[0] == 'Q'){ 75 scanf("%d%d", &a, &b); 76 printf("%lld ", Query(a, b, 1, n, 1)); 77 } 78 else{ 79 scanf("%d%d%lld", &a, &b, &c); 80 Update(a, b, c, 1, n, 1); 81 } 82 } 83 return 0; 84 }