您的位置:首页 > 其它

最大子串和

2014-09-01 11:09 148 查看
最大子串和

问题描述:

给定n个整数(可能为负数)组成的序列a[1],a[2],a[3],…,a
,求该序列如a[i]+a[i+1]+…+a[j]的子段和的最大值。当所给的整数均为负数时定义子段和为0,依此定义,所求的最优值为:
Max{0,a[i]+a[i+1]+…+a[j]},1<=i<=j<=n 例如,当(a[1],a[2],a[3],a[4],a[5],a[6])=(-2,11,-4,13,-5,-2)时,最大子段和为20。

算法:

1、暴力法。(复杂度O(n2))

略。

2、分治法。(复杂度O(nlogn))

将一个数组x一分为二记为x1、x2,最大子串和可能出现在三个x1、x2或x1、x2的交界处,记为c1、c2、c3。

伪代码如下:

function maxLen(l,r,x){
if(l>r) return 0;
if(l==r) return x[l];
m=(l+r)/2;
lmax=sum=0;
for(i=m;i>=l;i--){
sum+=x[i];
if(sum>lmax)
lmax=sum;
}
rmax=sum=0;
for(i=m+1;i<=r;i++){
sum+=x[i];
if(sum>rmax)
rmax=sum;
}
return max(lmax+rmax,maxLen(l,m),maxLen(m+1,r));
}





3、动态规划(复杂度O(n))

定义maxLenEndingHere为到包含当前下标最大子串长度。

maxLen为从开始到x[0..i]的最长子串长度。

递归公式:maxLen(0,j)=max(maxLen(0,j-1),maxLenEndingHere);

伪代码如下:

function maxLen(x,n){
maxLen=0;
maxLenEndingHere=0;
for(i=0;i<n;i++){
if(maxLenEndingHere+x[i]<0)
maxLenEndingHere=0;
else maxLenEndingHere+=x[i];
maxLen=max(maxLen,maxLenEndingHere,);
}
}




                                            
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: