Can you answer these queries III (line segment tree to find the maximum sub-segment sum of the interval)

Can you answer these queries III (the maximum sub-segment sum of the interval)

Blue book title Can you answer these queries III
Given a sequence A of length N, and M instructions (N≤500000, M≤100000), each instruction may be one of the following two:

  • "2 xy", change A[x] to y.
  • "1 xy", query the largest continuous sub-segment sum in the interval [x,y], that is, max(x≤l≤r≤y)∑ri=lA[i].

​ For each query, output an integer to indicate the answer.

Idea: In the
online segment tree, except for the interval endpoints, in the maintenance interval and sum sums u m , the largest sub-segment of the interval anddat datd a t , the largest continuous sub-segment at the left end andlmax lmaxl m a x , the largest continuous sub-segment at the right end andrmax rmaxr m a x
transfer equation changes:
sum (p) = sum (p ∗ 2) + sum (p ∗ 2 + 1) sum(p)=sum(p*2)+sum(p*2+1)s u m ( p )=s u m ( p2)+s u m ( p2+1)
r m a x ( p ) = m a x ( r m a x ( p ∗ 2 + 1 ) , s u m ( p ∗ 2 + 1 ) + r m a x ( p ∗ 2 ) ) rmax(p)=max(rmax(p*2+1),sum(p*2+1)+rmax(p*2)) rmax(p)=max(rmax(p2+1),s u m ( p2+1)+rmax(p2))
l m a x ( p ) = m a x ( l m a x ( p ∗ 2 ) , l m a x ( p ∗ 2 + 1 ) + s u m ( 2 ∗ p ) ) lmax(p)=max(lmax(p*2),lmax(p*2+1)+sum(2*p)) lmax(p)=max(lmax(p2),lmax(p2+1)+sum(2p))
d a t ( p ) = m a x ( d a t ( p ∗ 2 ) , m a x ( d a t ( p ∗ 2 + 1 ) , l m a x ( p ∗ 2 + 1 ) + r m a x ( p ∗ 2 ) ) ) dat(p)=max(dat(p*2),max(dat(p*2+1),lmax(p*2+1)+rmax(p*2))) d a t ( p )=m a x ( d a t ( p2),m a x ( d a t ( p2+1),lmax(p2+1)+rmax(p2)))

struct SegmentTree{
    
    
	int l,r;
	int dat,sum,lmax,rmax;
	#define l(x) tree[x].l
    #define r(x) tree[x].r
    #define dat(x) tree[x].dat
    #define sum(x) tree[x].sum
    #define lmax(x) tree[x].lmax
    #define rmax(x) tree[x].rmax
}tree[maxn*4];
int a[maxn];
int n,m;

void build(int p,int l,int r){
    
    
	l(p)=l,r(p)=r;
	if(l==r){
    
    
        dat(p)=a[l];sum(p)=a[l];lmax(p)=a[l];rmax(p)=a[l];return;
    }
	int mid=(l+r)/2;
	build(p*2,l,mid);
	build(p*2+1,mid+1,r);
	sum(p)=sum(p*2)+sum(p*2+1);
	rmax(p)=max(rmax(p*2+1),sum(p*2+1)+rmax(p*2));
	lmax(p)=max(lmax(p*2),lmax(p*2+1)+sum(2*p));
	dat(p)=max(dat(p*2),max(dat(p*2+1),lmax(p*2+1)+rmax(p*2)));
}

void change(int p,int x,int z){
    
    
	if(l(p)==r(p)){
    
    
		dat(p)=z;sum(p)=z;lmax(p)=z;rmax(p)=z;return;
	}
	int mid=(l(p)+r(p))/2;
	if(x<=mid) change(p*2,x,z);
    else change(p*2+1,x,z);
	sum(p)=sum(p*2)+sum(p*2+1);
	rmax(p)=max(rmax(p*2+1),sum(p*2+1)+rmax(p*2));
	lmax(p)=max(lmax(p*2),lmax(p*2+1)+sum(2*p));
	dat(p)=max(dat(p*2),max(dat(p*2+1),lmax(p*2+1)+rmax(p*2)));
}

SegmentTree ask(int p,int l,int r){
    
    
	if(l<=l(p)&&r>=r(p)) return tree[p];
	SegmentTree a,b,ans;
	a.sum=a.lmax=a.rmax=a.dat=b.sum=b.lmax=b.rmax=b.dat=-1*inf;
	ans.sum=0;
    int mid=(l(p)+r(p))/2;
    if(l<=mid){
    
    a=ask(p*2,l,r);ans.sum+=a.sum;}
    if(r>mid){
    
    b=ask(p*2+1,l,r);ans.sum+=b.sum;}
    ans.dat=max(max(a.dat,b.dat),a.rmax+b.lmax);
    ans.lmax=max(a.lmax,a.sum+b.lmax);
    ans.rmax=max(b.rmax,b.sum+a.rmax);
    if(l>mid)ans.lmax=max(ans.lmax,b.lmax);
    if(r<=mid)ans.rmax=max(ans.rmax,a.rmax);
    return ans;
}

int main(){
    
    
	cin>>n>>m;
	for(int i=1;i<=n;i++)
		cin>>a[i];
	build(1,1,n);
	while(m--){
    
    
        int op,x,y;
        cin>>op>>x>>y;
		if(op==2){
    
    
			change(1,x,y);
		}
		else {
    
    if(x>y)swap(x,y);cout<<ask(1,x,y).dat<<endl;}
	}
}

Guess you like

Origin blog.csdn.net/weixin_44986601/article/details/105759443