POJ - 3468
https://cn.vjudge.net/problem/POJ-3468
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll maxn = 4 * 1e5 + 500;
ll n,m;
struct SegTree
{
ll l;
ll r;
ll sum;
ll add;
};
SegTree segTree[maxn];
char c;
ll l,r,v;
void PushUp(ll i)
{
segTree[i].sum = segTree[i<<1].sum + segTree[i<<1|1].sum;
}
void PushDown(ll i)
{
if(segTree[i].add){
ll add = segTree[i].add;
ll len = segTree[i].r - segTree[i].l + 1;
segTree[i<<1].add += add;
segTree[i<<1|1].add += add;
segTree[i<<1|1].sum += len/2 * add;
segTree[i<<1].sum += (len-len/2) * add;
segTree[i].add = 0;
}
}
void Build(ll l, ll r, ll i)
{
segTree[i].l = l;
segTree[i].r = r;
segTree[i].add = 0;
if(l == r){cin>>segTree[i].sum; return;}
ll mid = l + r >> 1;
Build(l,mid,i<<1);
Build(mid+1,r,i<<1|1);
PushUp(i);
}
void Update(ll v, ll l, ll r, ll i)
{
if(l <= segTree[i].l && segTree[i].r <= r){
segTree[i].sum += v * (segTree[i].r - segTree[i].l + 1);
segTree[i].add += v;
return ;
}
PushDown(i);
ll mid = segTree[i].l + segTree[i].r >> 1;
ll ret = 0;
if(l > mid){
Update(v,l,r,i<<1|1);
}
else if(r <= mid){
Update(v,l,r,i<<1);
}
else{
Update(v,l,mid,i<<1);
Update(v,mid+1,r,i<<1|1);
}
PushUp(i);
return;
}
ll Query(ll l, ll r, ll i)
{
if(l <= segTree[i].l && segTree[i].r <= r){
return segTree[i].sum;
}
PushDown(i);
ll mid = segTree[i].l + segTree[i].r >> 1;
ll ret = 0;
if(l > mid){
ret += Query(l,r,i<<1|1);
}
else if(r <= mid){
ret += Query(l,r,i<<1);
}
else{
ret += Query(l,mid,i<<1);
ret += Query(mid+1,r,i<<1|1);
}
PushUp(i);
return ret;
}
int main()
{
//freopen("data.c", "r", stdin);
ios::sync_with_stdio(0);
cin.tie();
cout.tie();
while(cin>>n>>m){
Build(1,n,1);
while(m--){
cin>>c>>l>>r;
if(c == 'C') cin>>v,Update(v,l,r,1);
else if(c == 'Q') cout<<Query(l,r,1)<<endl;
}
}
return 0;
}