再把节点的信息传递到左右孩子的结点上; 解题思路:
代码如下:
#include <stdio.h>
#include <string.h>
using namespace std;
typedef long long LL;
const int maxn = 100010;
LL s[maxn],c[2][maxn];
int n,m;
void add(LL *c,int i,LL val)
{
while(i <= n)
{
c[i] += val;
i += i&-i;
}
}
LL sum(LL *c,int i,LL ret = 0)
{
while(i > 0)
{
ret += c[i];
i -= i&-i;
}
return ret;
}
int main()
{
char cmd[4];
LL x,y,z;
while(~scanf("%d%d",&n,&m))
{
memset(c,0,sizeof c);
for(int i = 1; i <= n; ++i)
{
scanf("%lld",s + i);
s[i] += s[i-1];
}
while(m--)
{
scanf("%s",cmd);
if(cmd[0] == ‘C‘)
{
scanf("%lld%lld%lld",&x,&y,&z);
add(c[0],x,z);
add(c[0],y+1,-z);
add(c[1],x,x*z);
add(c[1],y+1,-z*(y+1));
} else
{
scanf("%lld%lld",&x,&y);
printf("%lld\n",s[y] - s[x-1] + (y+1)*sum(c[0],y) - sum(c[1],y) - x*sum(c[0],x-1)