线段树
第一种写法
#include<iostream>
#include<cstdio>
#include<cmath>
#include<cstring>
#include<algorithm>
#define I long long
#define FO(i,a,b) for(R I i=a;i<=b;++i)
#define fo(i,a,b) for(R I i=a;i<b;++i)
#define ll long long
#define ls(x) (x<<1)
#define rs(x) (ls(x)|1)
CT I N =100005;
// CT I M = 200005;
// const I inf = 2747483647/3;
using namespace std;
ll sum[N<<2];
ll bt[N<<2];
ll len[N<<2];
I n,m;
void down(I son){
bt[ls(son)]+=bt[son];
bt[rs(son)]+=bt[son];
sum[ls(son)]+=bt[son]*len[ls(son)];
sum[rs(son)]+=bt[son]*len[rs(son)];
bt[son]=0;
}
void insert(I id,I v,I le=1,I re=n,I son=1) {
if(le==re){
sum[son]=v;
len[son]=1;
return ;
}
I mid=(le+re)>>1;
if (id<=mid) {
insert(id,v,le,mid,ls(son));
} else {
insert(id,v,mid+1,re,rs(son));
}
sum[son]=sum[ls(son)]+sum[rs(son)];
len[son]=len[ls(son)]+len[rs(son)];
}
void add(I l,I r,I k,I le=1,I re=n,I son=1){
if(l<=le&&re<=r){
sum[son]+=k*len[son];
bt[son]+=k;
return ;
}
I mid=(le+re)>>1;
down(son);
if(l<=mid){add(l,r,k,le,mid,ls(son));}
if(r>mid){add(l,r,k,mid+1,re,rs(son));}
sum[son]=sum[ls(son)]+sum[rs(son)];
}
ll getsum(I l,I r,I le=1,I re=n,I son=1){
if(l<=le&&re<=r){
return sum[son];
}
down(son);
I mid=(le+re)>>1;
ll ans=0;
if(l<=mid) ans+=getsum(l,r,le,mid,ls(son));
if(r>mid) ans+=getsum(l,r,mid+1,re,rs(son));
return ans;
}
int main(){
scanf("%lld%lld",&n,&m);
FO(i,1,n){
I x;
scanf("%lld",&x);
insert(i,x);
}
FO(i,1,m){
I x;
scanf("%lld",&x);
if (x==1) {
I l,r,k;
scanf("%lld%lld%lld",&l,&r,&k);
add(l,r,k);
} else {
I l,r;
scanf("%lld%lld",&l,&r);
cout<<getsum(l,r)<<endl;
}
}
return 0;
}
第二种写法
#include<iostream>
#include<cstdio>
using namespace std;
#define int long long
inline int ls(int x){return x<<1;}
inline int rs(int x){return x<<1|1;}
struct FFF{
int l,r;
int sum;
int tag;
int mid(){return l+r>>1;}
int len(){return r-l+1;}
}t[100000<<2];
int read(){
int s,f=1;
char ch;
while(!isdigit(ch=getchar()))(ch=='-')&&(f=-1);
for(s=ch-'0';isdigit(ch=getchar());s=((s+(s<<2))<<1)+ch-'0');
return s*f;
}
int n,m;
void pushup(int o){
t[o].sum=t[ls(o)].sum+t[rs(o)].sum;
}
void pushdown(int o){
int & v=t[o].tag;
t[ls(o)].tag+=v;
t[rs(o)].tag+=v;
t[ls(o)].sum+=v*t[ls(o)].len();
t[rs(o)].sum+=v*t[rs(o)].len();
v=0;
}
void build(int l=1,int r=n,int o=1){
t[o].l=l;t[o].r=r;
if(l==r){
t[o].sum=read();
return;
}
int mid=t[o].mid();
build(l,mid,ls(o));
build(mid+1,r,rs(o));
pushup(o);
}
void add(int l,int r,int k,int o=1){
if(l<=t[o].l&&t[o].r<=r){
t[o].sum+=k*t[o].len();
t[o].tag+=k;
return;
}
int mid=t[o].mid();
pushdown(o);
if(l<=mid){add(l,r,k,ls(o));}
if(r>mid){add(l,r,k,rs(o));}
pushup(o);
}
int getsum(int l,int r,int o=1){
if(l<=t[o].l&&t[o].r<=r){return t[o].sum;}
pushdown(o);
int mid=t[o].mid();
int ans=0;
if(l<=mid) ans+=getsum(l,r,ls(o));
if(r>mid) ans+=getsum(l,r,rs(o));
return ans;
}
signed main(){
n=read();m=read();
build();
while(m--){
int op=read(),l=read(),r=read(),x;
if(op==1){x=read();add(l,r,x);}
if(op==2){cout<<getsum(l,r)<<endl;}
}
return 0;
}

浙公网安备 33010602011771号