最大子数组问题/Maximum Subarray

Posted Make a commitment to your own

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了最大子数组问题/Maximum Subarray相关的知识,希望对你有一定的参考价值。

问题描述:

Find the contiguous subarray within an array (containing at least one number) which has the largest sum. 
For example, given the array [?2,1,?3,4,?1,2,1,?5,4], 
the contiguous subarray [4,?1,2,1] has the largest sum = 6.

问题分析(参考了算法导论第4章分治策略的内容):

为求一个含负数的一组数种,和为最大的子数组
这里使用分治的思想

首先,这一个子数组它只可能以3种方式存在:
完全在上半部分:low--mid
完全在下半部分:mid--high
或者跨越中点地存在:可理解为Arr[i..mid]+[mid+1..j]最大的元素和组成

 算法的思想:递归地寻求左、右部分的最大子数组和
最后合并每次递归结果的解(只保留最后最大的结果)

时间复杂度分析:

n=1 T(1)=Θ(1)
n>1 子问题——求解左子数组和右子数组;每组子问题求解花费T(n/2)
所以算法的运行时间T(n)递归式为:
T(n)= Θ(1)       ,n=1
              2T(n/2)  ,n>1
最后可以求解出T(n)=Θ(nlgn)

 1 #include<iostream>
 2 #include<climits>
 3 using namespace std;
 4 const int infinite=-9999;
 5 int Find_Max_Crossing_Subarray(int arr[],int low,int mid,int high)//扫描上半部分最大和、下半部分最大和,上下部分结合为跨越中点最大和
 6 {
 7 
 8     int left_sum=infinite;
 9     int right_sum=infinite;
10     int max_left=-1,max_right=-1,sum=0;
11     for(int i=mid; i>=low; i--)
12     {
13         sum+=arr[i];
14         if(sum>left_sum)
15         {
16             left_sum=sum;
17             max_left=i;
18         }
19     }
20     sum=0;
21     for(int j=mid+1; j<=high; j++)
22     {
23         sum+=arr[j];
24         if(sum>right_sum)
25         {
26             right_sum=sum;
27             max_right=j;
28         }
29     }
30     return (left_sum+right_sum);
31 }
32 int Find_Maximum_Subarray(int arr[],int low,int high)//
33 {
34     if(high==low)//只有一个元素的时候
35         return arr[low];
36     else
37     {
38         int mid=(low+high)/2;
39         int leftSum=Find_Maximum_Subarray(arr,low,mid);
40         int rightSum=Find_Maximum_Subarray(arr,mid+1,high);
41         int crossSum=Find_Max_Crossing_Subarray(arr,low,mid,high);
42         if(leftSum>=rightSum&&leftSum>=crossSum)
43             return leftSum;
44         else if(rightSum>=leftSum&&rightSum>=crossSum)
45             return rightSum;
46         else return crossSum;
47     }
48 }
49 int main()
50 {
51     int arr[10]= {5,2,8,-6,9,1,10,7,-13,9};
52     int ans=Find_Maximum_Subarray(arr,0,9);
53     cout<<ans<<endl;
54     return 0;
55 }

 

以上是关于最大子数组问题/Maximum Subarray的主要内容,如果未能解决你的问题,请参考以下文章

leetcode 53. Maximum Subarray 最大子数组和(中等)

[LintCode] Maximum Subarray 最大子数组

53. Maximum Subarray最大子数组

leetCode 53.Maximum Subarray (子数组的最大和) 解题思路方法

算法: 最大乘积子数组152. Maximum Product Subarray

53. Maximum Subarray(动态规划 求最大子数组)