Christophe_ @ 2023-07-05 20:24:06
// Problem: P3372 【模板】线段树 1
// Contest: Luogu
// URL: https://www.luogu.com.cn/problem/P3372
// Memory Limit: 125 MB
// Time Limit: 1000 ms
//
// Powered by CP Editor (https://cpeditor.org)
#include<bits/stdc++.h>
using namespace std;
#define int long long
inline int read(){
int ret=0,f=1;
char ch=getchar();
while(ch<'0'||ch>'9'){ if(ch=='-') f=-f; ch=getchar(); }
while(ch>='0'&&ch<='9') ret=ret*10+ch-'0',ch=getchar();
return ret*f;
}
inline void write(int x){
if(x<0){ putchar('-'); x=-x; }
if(x>9) write(x/10);
putchar(x%10+'0');
}
const int MAXN=1e6+7,minL=1,maxR=1e6+7;
int id=0;
struct Node{
int ls,rs;
int val,tag;
}tr[MAXN<<2];
void push_up(int p){
tr[p].val=tr[tr[p].ls].val+tr[tr[p].rs].val;
}
void push_down(int p,int l,int r){
if(l>=r) return;
int mid=(l+r-1)/2;
if(!tr[p].ls) tr[p].ls=++id;
if(!tr[p].rs) tr[p].rs=++id;
tr[tr[p].ls].val+=tr[p].tag*(mid-l+1);
tr[tr[p].ls].tag+=tr[p].tag;
tr[tr[p].rs].val+=tr[p].tag*(r-mid);
tr[tr[p].rs].tag+=tr[p].tag;
tr[p].tag=0;
}
void add(int l,int r,int x,int p=1,int cl=minL,int cr=maxR){
if(l==cl&&r==cr){
tr[p].val+=x*(cr-cl+1);
tr[p].tag+=x;
return;
}
int mid=(cl+cr-1)/2;
push_down(p,cl,cr);
if(r<=mid) add(l,r,x,tr[p].ls,cl,mid);
else if(l>mid) add(l,r,x,tr[p].rs,mid+1,cr);
else{
add(l,mid,x,tr[p].ls,cl,mid);
add(mid+1,r,x,tr[p].rs,mid+1,cr);
}
push_up(p);
}
int qry(int l,int r,int p=1,int cl=minL,int cr=maxR){
if(l==cl&&r==cr) return tr[p].val;
int mid=(cl+cr-1)/2;
push_down(p,cl,cr);
if(r<=mid) return qry(l,r,tr[p].ls,cl,mid);
else if(l>mid) return qry(l,r,tr[p].rs,mid+1,cr);
else{
int lans=qry(l,mid,tr[p].ls,cl,mid);
int rans=qry(mid+1,r,tr[p].rs,mid+1,cr);
return lans+rans;
}
}
int n,m;
signed main(){
n=read(),m=read();
for(int i=1;i<=n;++i){
int tmp=read();
add(i,i,tmp);
}
for(int i=1;i<=m;++i){
int op=read(),x=read(),y=read();
if(op==1){
int k=read();
add(x,y,k);
}else{
write(qry(x,y));
putchar('\n');
}
}
return 0;
}
动态开点线段树,拆区间写法,瞪了半天不知道哪里错了(
by Althemeta @ 2023-07-05 20:33:16
add和query
by Christophe_ @ 2023-07-05 20:53:38
好奇怪,把动态开点替换掉就能 AC ,这是为什么啊(动态开点为什么会假掉 qwq
by Christophe_ @ 2023-07-05 21:03:09
明白了,id
应该初始化为 1,相当于先开了一个根节点,占用一个编号;
如果初始化为 0 的话左儿子的编号就会与根节点相同,造成错误.