线段树区间和
#include<bits/stdc++.h>
using namespace std;
const int maxn=100005;
int n,m,p,ans,x,l,r,val;
struct node {
int l,r,w,f;//f为延迟标记
} tree[4*maxn+5];
void build(int k,int l,int r) { //建树
tree[k].l=l,tree[k].r=r;
if(tree[k].l==tree[k].r) {
scanf("%d",&tree[k].w);
return;
}
int mid=(l+r)/2;
build(k*2,l,mid);//左孩子
build(k*2+1,mid+1,r);//右孩子
tree[k].w=tree[k*2].w+tree[k*2+1].w;
}
void spread(int k) {//延迟标记
tree[k*2].f+=tree[k].f;
tree[k*2+1].f+=tree[k].f;
tree[k*2].w+=tree[k].f*(tree[k*2].r-tree[k*2].l+1);
tree[k*2+1].w+=tree[k].f*(tree[k*2+1].r-tree[k*2+1].l+1);
tree[k].f=0;
}
void ask(int k,int x) {//单点查询 ,x为查询位置
if(tree[k].l==tree[k].r) {
ans=tree[k].w;
return;
}
if(tree[k].f) spread(k);
int mid=(tree[k].l+tree[k].r)/2;
if(x<=mid) ask(2*k,x);
else ask(2*k+1,x);
}
void change(int k,int x,int val) {//单点修改 x修改位置,val增加的值
if(tree[k].l==tree[k].r) {
tree[k].w+=val;//
return;
}
if(tree[k].f) spread(k);
int mid=(tree[k].l+tree[k].r)/2;
if(x<=mid) change(2*k,x,val);
else change(2*k+1,x,val);
tree[k].w=tree[k*2].w+tree[k*2+1].w;
}
void query(int k,int x,int y) { //区间查询[x,y] 的和
if(tree[k].l>=x&&tree[k].r<=y) {
ans+=tree[k].w;
return;
}
if(tree[k].f) spread(k);
int mid=(tree[k].l+tree[k].r)/2;
if(x<=mid) query(2*k,x,y);
if(y>mid) query(2*k+1,x,y);
}
void modify(int k,int x,int y,int val) { //区间修改
if(tree[k].l>=x&&tree[k].r<=y) {
tree[k].w+=(tree[k].r-tree[k].l+1)*val;
tree[k].f+=val;
return;
}
if(tree[k].f) spread(k);
int mid=(tree[k].l+tree[k].r)/2;
if(x<=mid) modify(2*k,x,y,val);
if(y>mid) modify(2*k+1,x,y,val);
tree[k].w=tree[k*2].w+tree[k*2+1].w;
}
int main() {
scanf("%d%d",&n,&m);//n个节点,m个操作;
build(1,1,n);
while(m--) {
scanf("%d",&p);
ans=0;
if(p==1){//查询节点x的值 ,单点查询
scanf("%d",&x);
ask(1,x);
printf("%d\n",ans);
}else if(p==2){//节点x增加val,单点修改
scanf("%d%d",&x,&val);
change(1,x,val);
}else if(p==3){//区间查询
scanf("%d%d",&l,&r);
query(1,l,r);
printf("%d\n",ans);
}else if(p==4){//区间[l,r]都增加val,区间修改
scanf("%d%d%d",&l,&r,&val);
modify(1,l,r,val);
}
}
}
/*
9 8
1 2 3 4 5 6 7 8 9
1 5
3 4 8
2 5 100
1 5
3 4 9
4 2 6 77
1 6
3 1 9
ans:
5
30
105
139
83
530
*/