434
社区成员
发帖
与我相关
我的任务
分享

伪代码:
算法 MaxSum(a,left,right)
输入:数组a,left,right(左右边界)
输出:最大子段和sum及子段边界
if |a|=1 then 输出元素(值为负输出0)
mid=(left+right)/2
leftsum<-MaxSum(a,left,mid)
rightsum<-MaxSum(a.mid+1,right)
S1<-a1[mid] //从mid向左
S2<-a2[mid+1] //从mid向右
sum <- S1+S2
if leftsum>sum then sum<-leftsum
if rightsum>sum then sun<-rightsum
在数组的 mid = (right-left)/2+1 位置处分开。形成两个子数组。
那么,最大子段和可能出现在三个位置:
可能出现在左子数组
可能出现在右子数组
可能出现在包含mid及其左右两边的子数组
下面考虑 三种情况的计算方法:
第一种情况: 计算 left 到 mid 的最大和,记作 leftSum
第二种情况: 计算从 mid+1 到 right的最大和,记作 rightSum
第三种情况: 跨边界的和, 以mid为中心分别向两边计算和。
a.从 mid出发,每次向左边扩张一步,并且记录当前的值S1,如果当前的和比上次的和大,就更新S1,一直向左扩张到位置 Left。
b.从 mid+1出发,每次扩张一步,计算当前的和 为S2,如果当前的值比上次的和大,就更新S2的值,一直向右扩张到位置Right。
c.计算过mid的连续值的和,S1+S2的值 Sum。 这个就是跨边界的和。
上面三种情况考虑计算完成后,最后一步就是,比较三个值中的最大值,取最大值就可以了。
分解子问题时间复杂度为O(1)
合并子问题算法时间复杂度为O(1)
求解子问题的时候,分成两段进行求解,每段是原来的一半长度,因所以时间复杂度为2T(n/2)
最后得到T(n)=2T(n/2)+O(n),计算得时间复杂度为O(nlogn)
分治法的设计思想:将一个难以直接解决的大问题,分割成一些规模较小的相同问题,以便各个击破,分而治之。
但在问题规模很小的时候,这种方法并不是很适合。
总结:这种化大问题为小问题,就如积跬步以至千里,在我们的日常生活中面对各种难题都可以多少采用一下这种方法,走一步再走一步,总会成功的