rt
#include <iostream>
#define int long long
using namespace std;
const int kMaxN=1e5+1;
int a[kMaxN];
struct XDS
{
int l,r;//每个节点的左儿子和右二字
int z,add;
}tr[kMaxN*4];
int n,m;
void Build(int where,int le,int ri)//建树
{
tr[where].l=le;
tr[where].r=ri;
if(le==ri)
{
tr[where].z=a[le];
return;
}
int mid=(le+ri)/2;
Build(where*2,le,mid);//建左儿子和右二字
Build(where*2+1,mid+1,ri);
tr[where].z=tr[where*2].z+tr[where*2+1].z;
}
void Solve(int where)//懒标记处理
{
if(tr[where].add==0)
{
return;
}
tr[where*2].z+=tr[where].add*(tr[where*2].r-tr[where*2].l+1);
tr[where*2+1].z=tr[where].add*(tr[where*2+1].r-tr[where*2+1].l+1);
tr[where*2].add+=tr[where].add;
tr[where*2+1].add+=tr[where].add;
tr[where].add=0;
}
void Update(int where,int le,int ri,int k)//区间修改
{
if(tr[where].l>=le&&tr[where].r<=ri)
{
tr[where].z+=k*(tr[where].r-tr[where].l+1);
tr[where].add+=k;
return;
}
Solve(where);
int mid=(tr[where].r+tr[where].l)/2;
if(mid>=le)
{
Update(where*2,le,mid,k);
}
if(mid<ri)
{
Update(where*2+1,mid+1,ri,k);
}
tr[where].z+=tr[where*2].z+tr[where*2+1].z;
}
int Get(int where,int le,int ri)//区间查询
{
//cout<<where<<" "<<le<<" "<<ri<<"\n";
if(tr[where].l>=le&&tr[where].r<=ri)
{
return tr[where].z;
}
Solve(where);
int sum=0;
int mid=(tr[where].l+tr[where].r)/2;
if(mid>=le)
{
sum+=Get(where*2,le,mid);
}
if(mid<ri)
{
sum+=Get(where*2+1,mid+1,ri);
}
return sum;
}
signed main()
{
cin>>n>>m;
for(int i=1;i<=n;i++)
{
cin>>a[i];
}
Build(1,1,n);
for(int i=1;i<=m;i++)
{
int a;
cin>>a;
if(a==1)
{
int x,y,k;
cin>>x>>y>>k;
Update(1,x,y,k);
}
else
{
int x,y;
cin>>x>>y;
cout<<Get(1,x,y)<<"\n";
}
}
return 0;
}