http://poj.org/problem?id=3468
整段更新,整段查询
PushUp(int rt) 是把当前结点的信息更新到父结点
PushDown(int rt) 是把当前结点的信息更新到儿子结点
延迟标记:
简单来说就是每次更新的时候不要更新到底,用延迟标记
使得更新延迟到下次需要更新or询问到的时候
/* * 整段更新,整段查询 * PushUp(int rt) 是把当前结点的信息更新到父结点 * PushDown(int rt) 是把当前结点的信息更新到儿子结点 * 延迟标记: * 简单来说就是每次更新的时候不要更新到底,用延迟标记 * 使得更新延迟到下次需要更新or询问到的时候 * */ #include <cstdio> #include <cstring> #include <algorithm> using namespace std; typedef long long LL; #define LL(x) (x<<1) #define RR(x) (x<<1|1) #define N 111111 struct node { int l, r; LL add, sum; }tree[N*4]; int num[N]; void PushUp(int rt) { tree[rt].sum = tree[LL(rt)].sum + tree[RR(rt)].sum; } void PushDown(int rt, int len) { if(tree[rt].add) { tree[LL(rt)].add += tree[rt].add; tree[RR(rt)].add += tree[rt].add; tree[LL(rt)].sum += tree[rt].add*(len-(len>>1)); tree[RR(rt)].sum += tree[rt].add*(len>>1); tree[rt].add = 0; } } void build(int rt, int l, int r) { tree[rt].l = l, tree[rt].r = r, tree[rt].add = 0; if(l == r) { tree[rt].sum = num[l]; return ; } int mid = (l + r) >> 1; build(LL(rt), l, mid); build(RR(rt), mid+1, r); PushUp(rt); } void update(int rt, int l, int r, int val) { if( l <= tree[rt].l && tree[rt].r <= r) { tree[rt].add += val; tree[rt].sum += val*(tree[rt].r - tree[rt].l + 1); return ; } PushDown(rt, tree[rt].r - tree[rt].l + 1); int mid = ( tree[rt].l + tree[rt].r) >> 1; if( l <= mid) update(LL(rt), l, r, val); if( r > mid) update(RR(rt), l, r, val); PushUp(rt); } LL query(int rt, int l, int r) { if( l <= tree[rt].l && tree[rt].r <= r) { return tree[rt].sum; } PushDown(rt, tree[rt].r - tree[rt].l + 1); int mid = ( tree[rt].l + tree[rt].r) >> 1; LL ret = 0; if( l <= mid) ret += query(LL(rt), l, r); if( r > mid) ret += query(RR(rt), l, r); return ret; } int main() { int n, q, i; scanf("%d%d",&n,&q); for(i=1; i<=n; ++i) scanf("%d",&num[i]); build(1,1,n); // for(i=1; i<=n; ++i) // { // printf("%d %d:%lld\n",tree[i].l, tree[i].r, tree[i].sum); // } while(q--) { char cmd[10]; int a, b, c; scanf("%s",cmd); if(cmd[0]=='Q') { scanf("%d%d",&a,&b); printf("%I64d\n",query(1,a,b)); }else { scanf("%d%d%d",&a,&b,&c); update(1,a,b,c); } } return 0; }