一、以伪代码描述最大字段和的分治算法
一共有三种可能:
1.在[1, n/2]这个区域内在 2.[n/2+1, n]这个区域内 3.起点位于[1,n/2],终点位于[n/2+1,n]内
所以可以以n/2为终点向左移动求出leftmax,以n/2+1为起点往右移动求出rightmax,第三种情况是leftmax+rightmax
2.代码:
int max(int a[],int l,int r)
{
if(right==left)
{
if(a[left]>0)
return a[left];
else
return 0;
}
int mid=(l+r)/2;
int lMax=max(a,left,mid);
int rMax=max(a,mid+1,right);
int sum=0;
int leftmax=0;
for(int i=mid;i>=left;i--)
{
sum+=a[i];
if(sum>leftmax)
leftmax=sum;
}
sum=0;
int rightmax=0;
for(int i=mid+1;i<=right;i++)
{
sum+=a[i];
if(sum>rightmax)
rightmax=sum;
}
int ret=leftmax+rightmax;
if(ret<lMax)
ret= lMax;
if(ret< rMax)
ret=rMax;
return ret;
}
3.时间复杂度为O(nlogn)
二、分治法的体会和思考:
分治法是将一个很难解决的大问题拆成一个个规模较小的相同问题,这样能将这个难解决的问题变的简单一点。分治法的步骤是首先将问题分解成一些易解决的子问题,第二步利用递归解决子问题,第三步将子问题合并。让我最能感受到分治法的妙处的是归并排序,归并排序能划分成相同数量的集合进行排序最后将子集合并。分治法也能减少时间复杂度。分治法也需要一定的练习才能掌握,我还需要更加深入的思考和练习才能掌握分治法。