![[tem]线段树(白书版) [tem]线段树(白书版)](https://image.shishitao.com:8440/aHR0cHM6Ly9ia3FzaW1nLmlrYWZhbi5jb20vdXBsb2FkL2NoYXRncHQtcy5wbmc%2FIQ%3D%3D.png?!?w=700)
个人感觉有点坑
add用的标记永久化
set用的标记下传
#include <iostream>
#include <cstdio>
#include <algorithm>
#include <cstring>
#define lson o<<1,l,m
#define rson (o<<1)+1,m+1,r
#define ls o<<1
#define rs (o<<1)+1
using namespace std;
const int N=1e4,INF=1e9; int minv[N<<],maxv[N<<],sumv[N<<];
int addv[N<<],setv[N<<];
int ql,qr,p,v; //point
int queryMin(int o,int l,int r){
int m=l+((r-l)>>),ans=INF;
if(ql<=l&&r<=qr) return minv[o];
if(ql<=m) ans=min(ans,queryMin(lson));
if(m+<=qr) ans=min(ans,queryMin(rson));
return ans;
} void change(int o,int l,int r){
int m=l+((r-l)>>);
if(l==r)
minv[o]=v;
else{
if(p<=m) change(lson);
else change(rson);
minv[o]=min(minv[ls],minv[rs]);
}
} //add
int _min,_max,_sum;
void maintain(int o,int l,int r){
sumv[o]=minv[o]=maxv[o]=;//!!
if(l<r){
sumv[o]=sumv[ls]+sumv[rs];
minv[o]=min(minv[ls],minv[rs]);
maxv[o]=max(maxv[ls],maxv[rs]);
}
minv[o]+=addv[o];
maxv[o]+=addv[o];
sumv[o]+=addv[o]*(r-l+);
} void addRange(int o,int l,int r){
if(ql<=l&&r<=qr)
addv[o]+=v;
else{
int m=(r+l)>>;
if(ql<=m) addRange(lson);
if(m+<=qr) addRange(rson);
}
maintain(o,l,r);
} void queryRange(int o,int l,int r,int add){
if(ql<=l&&r<=qr){
_sum+=sumv[o]+add*(r-l+);
_min=min(_min,minv[o]+add);
_max=max(_max,maxv[o]+add);
}else{
int m=(r+l)>>;
if(ql<=m) queryRange(lson,add+addv[o]);
if(m+<=qr) queryRange(rson,add+addv[o]);
}
} //set
void mt(int o,int l,int r){
if(setv[o]>=){
sumv[o]=setv[o]*(r-l+);
minv[o]=maxv[o]=setv[o];
}else if(l<r){
sumv[o]=sumv[ls]+sumv[rs];
minv[o]=min(minv[ls],minv[rs]);
maxv[o]=max(maxv[ls],maxv[rs]);
}
} void pushDown(int o){
if(setv[o]>=){
setv[ls]=setv[rs]=setv[o];
setv[o]=-;
}
} void setRange(int o,int l,int r){
if(ql<=l&&r<=qr) setv[o]=v;
else {
pushDown(o);
int m=(r+l)>>;
if(ql<=m) setRange(lson); else mt(lson);
if(m+<=qr) setRange(rson); else mt(rson);
}
mt(o,l,r);
} void queryRange(int o,int l,int r){
if(setv[o]>=){
_sum+=setv[o]*(r-l+);
_min=min(_min,setv[o]);
_max=max(_max,setv[o]);
}else if(ql<=l&&r<=qr){
_sum+=sumv[o];
_min=min(_min,minv[o]);
_max=max(_max,maxv[o]);
}else{
int m=(r+l)>>;
if(ql<=m) queryRange(lson);
if(m+<=qr) queryRange(rson);
}
} int n,t;
int main(int argc, const char * argv[]) { //freopen("in.txt","r",stdin);
//freopen("2.txt","w",stdout); cin>>n>>t;
for(int i=;i<=n;i++){
cin>>v;
ql=qr=i;
addRange(,,n);
} // for(int i=1;i<=n<<1;i++) printf("%d %d %d %d\n",i,sumv[i],minv[i],maxv[i]); while(t--){
int flag;
cin>>flag;
if(flag==){
cin>>ql>>qr;
_sum=;_min=INF;_max=-INF;
queryRange(,,n,);
printf("%d\n",_sum);
}else{
cin>>ql>>qr>>v;
addRange(,,n);
_sum=;_min=INF;_max=-INF;
queryRange(,,n,);
printf("%d\n",_sum);
}
} return ;
}