分块80分最后一个点T了 代码
#include<bits/stdc++.h>
using namespace std;
typedef long long ll;
const ll N=4e5+7 ,M=1003;
ll add[M], sum[M], n, a[N], len, m;
ll get(ll i) {
return i/len;
}
inline ll read(){
int x=0, f=1;
char c=getchar();
while(c<'0'||c>'9'){
if(c=='-')f=-1;c=getchar();
}
while(c>='0'&&c<='9')x=x*10+c-'0',c=getchar();
return x*f;
}
void change(int l, int r, int d) {
if(get(l)==get(r)) {
for(int i=l; i<=r; ++i) {
a[i]+=d;
sum[get(i)]+=d;
}
} else {
int i=l, j=r;
while(get(i)==get(l)) {
a[i]+=d;
sum[get(i)]+=d;
++i;
}
while(get(j)==get(r)) {
a[j]+=d;
sum[get(j)]+=d;
j--;
}
for(int k=get(i); k<=get(j); ++k) {
sum[k]+=(ll)len*d;
add[k]+=d;
}
}
return ;
}
ll query(int l, int r) {
ll res=0;
if(get(l)==get(r)) {
for(int i=l; i<=r; ++i) {
res+=a[i]+add[get(i)];
}
} else {
int i=l, j=r;
while(get(i)==get(l)) {
res+=a[i]+add[get(i)];
++i;
}
while(get(j)==get(r)) {
res+=a[j]+add[get(j)];
--j;
}
for(int k=get(i); k<=get(j); ++k) {
res+=sum[k];
}
}
return res;
}
int main() {
n=read(),m=read();
len=sqrt(n);
for(int i=1; i<=n; ++i) {
a[i]=read();
sum[get(i)]+=a[i];
}
for(int i=1; i<=m; ++i) {
int opt, l, r, c;
opt=read();
if(opt==1) {
l=read(),r=read(),c=read();
change(l,r,c);
} else if(opt==2) {
c=read();
a[1]+=c,sum[0]+=c;
} else if(opt==3) {
c=read();
a[1]-=c,sum[0]-=c;
} else if(opt==4) {
l=read(),r=read();
printf("%lld\n",query(l,r));
} else if(opt==5) {
printf("%lld\n",a[1]+add[0]);
}
}
return 0;
}