最大子段和

题意:给出一段序列,选出其中连续且非空的一段使得这段和最大。

O(N^2)做法:

O(n)求出前缀和,O(N^2)枚举每个区间即可。

代码就不给了。

O(N)做法:

每一个数字,它能够加入前面的区间,也能重新开始一个区间。所以我们以此为两种状态。

状态转移方程:

f[i]=max(f[i-1]+a[i],a[i]).

表示 包含i的区间的最大值,如果f[i-1]为负数,那么肯定要开辟一个新的区间,此区间暂时只有一个元素即a[i]。

 代码:

 

#include<iostream>
#include<cstdio>
#include<cstring>
#define ll long long int
using namespace std;
const int N=2005;
ll n,a[N],f[N],ans=-0x3f3f3f3f;
int main(){
    scanf("%lld",&n);
    for(ll i=1;i<=n;i++)
    scanf("%lld",&a[i]);
    for(ll i=1;i<=n;i++){
    f[i]=max(f[i-1]+a[i],a[i]);//加入前一区间 换新的区间
    ans=max(ans,f[i]);
    }
    printf("%lld",ans);
    return 0;
}

 

posted @ 2018-10-01 19:25  zxza695  阅读(168)  评论(0编辑  收藏  举报

Contact with me