zoukankan      html  css  js  c++  java
  • codevs 3981 动态最大子段和(线段树)

    题目传送门:codevs 3981 动态最大子段和 

    题目描述 Description

    题目还是简单一点好... 

    有n个数,a[1]到a[n]。

    接下来q次查询,每次动态指定两个数l,r,求a[l]到a[r]的最大子段和。

    子段的意思是连续非空区间。

    输入描述 Input Description

    第一行一个数n。

    第二行n个数a[1]~a[n]。

    第三行一个数q。

    以下q行每行两个数l和r。

    输出描述 Output Description

    q行,每行一个数,表示a[l]到a[r]的最大子段和。

    样例输入 Sample Input

    7
    2 3 -233 233 -23 -2 233
    4
    1 7
    5 6
    2 5
    2 3

    样例输出 Sample Output

    441
    -2
    233
    3

    数据范围及提示 Data Size & Hint

    对于50%的数据,q*n<=10000000。

    对于100%的数据,1<=n<=200000,1<=q<=200000。

    a[1]~a[n]在int范围内,但是答案可能超出int范围。

    数据保证1<=l<=r<=n。

    空间128M,时间1s。

    题目大意:

      求解区间 a[l]~a[r] 的最大子段和

    解题思路:

      用线段树维护区间最大值。开几个变量存区间和sum,完全在左区间的最大值max_l,完全在右区间的最大值max_r,跨左右区间的最大值max。

     1 #include <bits/stdc++.h>
     2 #define lson rt<<1,l,mid
     3 #define rson rt<<1|1,mid+1,r
     4 using namespace std;
     5 const int N = 200000 + 10;
     6 typedef long long int ll;
     7 struct node
     8 {
     9     int l,r;
    10     ll max_,max_l,max_r,sum;
    11 } a[N<<2];
    12 int n,q,x,y;
    13 ll ans;
    14 void up(int rt)
    15 {
    16     a[rt].max_=max(max(a[rt<<1].max_,a[rt<<1|1].max_),a[rt<<1].max_r+a[rt<<1|1].max_l);
    17     a[rt].max_l=max(a[rt<<1].max_l,a[rt<<1].sum+a[rt<<1|1].max_l);
    18     a[rt].max_r=max(a[rt<<1|1].max_r,a[rt<<1|1].sum+a[rt<<1].max_r);
    19     a[rt].sum=a[rt<<1].sum+a[rt<<1|1].sum;
    20 }
    21 void build(int rt,int l,int r)
    22 {
    23     a[rt].l=l,a[rt].r=r;
    24     if (l==r)
    25     {
    26         scanf("%lld",&a[rt].max_);
    27         a[rt].max_l=a[rt].max_r=a[rt].sum=a[rt].max_;
    28         return ;
    29     }
    30     int mid = (l+r)>>1;
    31     build(lson);
    32     build(rson);
    33     up(rt);
    34 }
    35 void query(int rt,int L,int R,ll &ans,ll &ansl,ll &ansr)
    36 {
    37     if (L<=a[rt].l&&a[rt].r<=R)
    38     {
    39         ans=a[rt].max_;
    40         ansl=a[rt].max_l;
    41         ansr=a[rt].max_r;
    42         return ;
    43     }
    44     int mid=(a[rt].l+a[rt].r)>>1;
    45     if (mid>=R) query(rt<<1,L,R,ans,ansl,ansr);
    46     else if (mid<L) query(rt<<1|1,L,R,ans,ansl,ansr);
    47     else
    48     {
    49         ll lans=0,lansl=0,lansr=0,rans=0,ransl=0,ransr=0;
    50         query(rt<<1,L,R,lans,lansl,lansr);
    51         query(rt<<1|1,L,R,rans,ransl,ransr);
    52         ans=max(max(lans,rans),lansr+ransl);
    53         ansl=max(lansl,ransl+a[rt<<1].sum);
    54         ansr=max(ransr,lansr+a[rt<<1|1].sum);
    55     }
    56 }
    57 int main()
    58 {
    59     scanf("%d",&n);
    60     build(1,1,n);
    61     for ( scanf("%d",&q); q; q--)
    62     {
    63         scanf("%d%d",&x,&y);
    64         ll ans=0,ansl=0,ansr=0;
    65         query(1,x,y,ans,ansl,ansr);
    66         printf("%lld
    ",ans);
    67     }
    68     return 0;
    69 }
    View Code
  • 相关阅读:
    MySQL 约束
    MySQL 基础
    LeetCode-Backtracking-Easy 回溯算法
    cookie session区别
    mac环境下支持PHP调试工具xdebug,phpstorm监听
    dede修改移动文档的js
    ajax是怎么发请求的和浏览器发的请求一样吗?cookie
    linux命令
    mysql里的sql函数
    nginx启动
  • 原文地址:https://www.cnblogs.com/l999q/p/9454303.html
Copyright © 2011-2022 走看看