题目链接
题意
![在这里插入图片描述](https://img-blog.csdnimg.cn/85145d1a00574a36932468ea5e02940e.png?x-oss-process=image/watermark,type_ZHJvaWRzYW5zZmFsbGJhY2s,shadow_50,text_Q1NETiBAU3VuZGF5SmVycnk=,size_20,color_FFFFFF,t_70,g_se,x_16#pic_center)
求区间的最大连续子段和和单点修改
#include<bits/stdc++.h>
#define ls u<<1
#define rs u<<1|1
#define sc scanf
#define pr printf
using namespace std;
const int maxn = 5e5 + 100;
int a[maxn];
struct segtree{
int l,r;
int sum,lmax,rmax,mx;
}tr[maxn * 4];
void pushup(segtree &u,segtree &l, segtree &r){
u.sum = l.sum + r.sum;
u.lmax = max(l.lmax,l.sum + r.lmax);
u.rmax = max(r.rmax,r.sum + l.rmax);
u.mx = max(max(l.mx,r.mx),l.rmax + r.lmax);
}
void build(int u,int l,int r){
if(l == r){
tr[u]={l,r,a[r],a[r],a[r],a[r]};
}
else{
tr[u]={l,r};
int mid = l+r >> 1;
build(ls,l,mid);
build(rs,mid+1,r);
pushup(tr[u],tr[ls],tr[rs]);
}
}
void update(int u, int x, int v){
if(tr[u].l == x && tr[u].r == x)tr[u] = {x,x,v,v,v,v};
else{
int mid = tr[u].l + tr[u].r >> 1;
if(x <= mid)update(ls, x, v);
else update(rs, x, v);
pushup(tr[u],tr[ls],tr[rs]);
}
}
segtree query(int u, int l, int r){
if(tr[u].l >= l && tr[u].r <= r)return tr[u];
else{
int mid = tr[u].l + tr[u].r >> 1;
if(r <= mid)return query(ls, l, r);
else if(l > mid)return query(rs, l, r);
else{
segtree L = query(ls, l, r);
segtree R = query(rs, l, r);
segtree res;
pushup(res, L, R);
return res;
}
}
}
int main(){
int n,m;
sc("%d%d",&n,&m);
for(int i = 1; i <= n ;i++)sc("%d",&a[i]);
build(1, 1 ,n);
while(m--){
int op,x,y;
sc("%d%d%d",&op,&x,&y);
if(op == 1){
if(x > y)swap(x,y);
pr("%d\n",query(1, x, y).mx);
}else{
update(1, x, y);
}
}
}