Q__A__Q @ 2023-06-27 23:46:55
// 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;
typedef long long ll;
#define int ll
const int maxn=4e5+10;
const int inf=1e9+7;
int n,m,ans,a[maxn],sum[maxn],tag[maxn];
inline int read() {
int s=0,w=1;
char ch=getchar();
while(!isdigit(ch)) {
if(ch=='-')w=-1;
ch=getchar();
}
while(isdigit(ch)) s=s*10+ch-'0',ch=getchar();
return s*w;
}
inline void write(int x) {
if(x<0) putchar('-'),x=-x;
if(x>9) write(x/10);
putchar(x%10+'0');
}
inline void pushup(int rt) {
sum[rt]=sum[rt<<1]+sum[rt<<1|1];
}
inline void build(int rt,int l,int r) {
if(l==r) {
sum[rt]=a[l];
return;
}
int mid=(l+r)>>1;
build(rt<<1,l,mid);
build(rt<<1|1,mid+1,r);
pushup(rt);
}
inline void pushdown(int rt,int ln,int rn) {
if(tag[rt]) {
tag[rt<<1]+=tag[rt];
tag[rt<<1|1]+=tag[rt];
sum[rt<<1]+=tag[rt]*ln;
sum[rt<<1|1]+=tag[rt]*rn;
tag[rt]=0;
}
}
inline void update(int x,int y,int c,int l,int r,int rt) {
if(x<=l&&y>=r) {
sum[rt]+=c*(r-l+1);
tag[rt]+=c;
return;
}
int mid=(l+r)>>1;
pushdown(rt,mid-l+1,r-mid);
if(x<=mid) update(x,y,c,l,mid,rt<<1);
if(y>mid) update(x,y,c,mid+1,r,rt<<1|1);
pushup(rt);
}
inline int query(int x,int y,int l,int r,int rt) {
if(l==r) {
return sum[rt];
}
int mid=(l+r)>>1,ans=0;
pushdown(rt,mid-l+1,r-mid);
if(x<=mid) ans+=query(x,y,l,mid,rt<<1);
if(y>mid) ans+=query(x,y,mid+1,r,rt<<1|1);
return ans;
}
signed main() {
// freopen(".in","r",stdin);
// freopen(".out","w",stdout);
n=read(),m=read();
for(int i=1;i<=n;++i) a[i]=read();
build(1,1,n);
while(m--) {
int op=read(),x,y,k;
if(op==1) {
x=read(),y=read(),k=read();
update(x,y,k,1,n,1);
}
else {
x=read(),y=read();
write(query(x,y,1,n,1));
puts("");
}
}
return 0;
}
by SpeedStar @ 2023-06-28 01:41:46
@QAQ 查询函数里的第一句 l == r
by QAQ__ @ 2023-06-28 07:13:49
把 query 函数改成这样就不 TLE 了,但是还是 WA.
inline int query(int x,int y,int l,int r,int rt) {
if(l==x&&r==y) {
return sum[rt];
}
int mid=(l+r)>>1,ans=0;
pushdown(rt,mid-l+1,r-mid);
if(x<=mid) ans+=query(x,mid,l,mid,rt<<1);
if(y>mid) ans+=query(mid+1,y,mid+1,r,rt<<1|1);
return ans;
}
顺便问一下是不是看着算进写的(
by Q__A__Q @ 2023-06-28 21:54:05
@QAQ__ 应该改成l>=x&&r<=y吧