Description
You have N integers, A1, A2, ... , AN. You need to deal with two kinds of operations. One type of operation is to add some given number to each number in a given interval. The other is to ask for the sum of numbers in a given interval.
Input
The first line contains two numbers N and Q. 1 ≤ N,Q ≤ 100000.
The second line contains N numbers, the initial values of A1, A2, ... , AN. -1000000000 ≤ Ai ≤ 1000000000.
Each of the next Q lines represents an operation.
"C a b c" means adding c to each of Aa, Aa+1, ... , Ab. -10000 ≤ c ≤ 10000.
"Q a b" means querying the sum of Aa, Aa+1, ... , Ab.
Output
You need to answer all Q commands in order. One answer in a line.
Sample Input
1 2 3 4 5 6 7 8 9 10
Q 4 4
Q 1 10
Q 2 4
C 3 6 3
Q 2 4
Sample Output
55
9
15
HINT
The sums may exceed the range of 32-bit integers.
#include<cmath> #include<cstdio> #include<cstring> #include<cstdlib> #include<algorithm> using namespace std; typedef long long ll; struct trnode{ int l,r,lc,rc; ll c,add; bool lazy; }tr[210000];int trlen; void bt(int l,int r) { int now=++trlen; tr[now].l=l;tr[now].r=r;tr[now].c=0ll; tr[now].lc=tr[now].rc=-1;tr[now].add=0ll,tr[now].lazy=false; if(l<r) { int mid=(l+r)/2; tr[now].lc=trlen+1;bt(l,mid); tr[now].rc=trlen+1;bt(mid+1,r); } } void update(int x) { int lc=tr[x].lc,rc=tr[x].rc; tr[lc].c+=(tr[lc].r-tr[lc].l+1)*tr[x].add;tr[lc].add+=tr[x].add; tr[rc].c+=(tr[rc].r-tr[rc].l+1)*tr[x].add;tr[rc].add+=tr[x].add; tr[x].add=0;tr[x].lazy=false; tr[lc].lazy=1;tr[rc].lazy=1; } void change(int now,int l,int r,ll c) { if(tr[now].l==l&&tr[now].r==r){ tr[now].c+=(tr[now].r-tr[now].l+1)*c; tr[now].add+=c;tr[now].lazy=true; return ; } int lc=tr[now].lc,rc=tr[now].rc,mid=(tr[now].l+tr[now].r)/2; if(tr[now].lazy==true)update(now); if(r<=mid)change(lc,l,r,c); else if(mid+1<=l)change(rc,l,r,c); else { change(lc,l,mid,c); change(rc,mid+1,r,c); } tr[now].c=tr[lc].c+tr[rc].c; } ll findsum(int now,int l,int r) { if(tr[now].l==l&&tr[now].r==r)return tr[now].c; if(tr[now].lazy==true)update(now); int lc=tr[now].lc,rc=tr[now].rc,mid=(tr[now].l+tr[now].r)/2; if(mid+1<=l)return findsum(rc,l,r); else if(r<=mid)return findsum(lc,l,r); else return findsum(lc,l,mid)+findsum(rc,mid+1,r); } int n,m; int main() { scanf("%d%d",&n,&m); trlen=0;bt(1,n); for(int i=1;i<=n;i++) { ll x; scanf("%lld",&x); change(1,i,i,x); } char st[6]; while(m--) { scanf("%s",st+1); if(st[1]==‘Q‘){ int l,r; scanf("%d%d",&l,&r);if(l>r)swap(l,r); printf("%lld\n",findsum(1,l,r)); } else { int x,y;ll c; scanf("%d%d%lld",&x,&y,&c);if(x>y)swap(x,y); change(1,x,y,c); } } return 0; }
by_lmy