Maximum subarray is a typical entry-level dynamic programming problem, and this kind of question usually pops up in the algorithm test during the interviews.
Maximum subarray 是一个典型的动态编程入门问题,并且这类问题经常出现在大厂的算法面试中。
The common scenario of the problem is:
通常这一问题的描述为:
Given an integer array nums
, find the contiguous subarray (containing at least one number) which has the largest sum and return its sum.
已知一int数组,在数组中找到连续元素组成的最大和,并返回。
Input: nums = [-2,1,-3,4,-1,2,1,-5,4]
Output: 6
Explanation: [4,-1,2,1] has the largest sum = 6.
For such a problem, the potential solutions usually include the brute force approach and Kadane's algorithm.
解决这类问题通常有两种方法,一种是遍历所有可能,另一种是Kadane算法。
The brute force approach basically iterates all the elements in the array and try to detect all the combinations of its additions to find the maximum num like this:
遍历并计算类似于冒泡排序,需要依次计算所有的和,并判断是否为最大:
According to the abstraction of the problem, we can use the following java code to achieve that:
以下是java代码实现:
public static int maxSubArrayEx(int[] nums) {
if(nums.length==1)
return nums[0];
int max = 0;
int subMax = 0;
for(int i=0;i<nums.length;i++)
{
int tem = nums[i];
for(int j=i+1;j<nums.length;j++)
{
tem += nums[j];
subMax = Math.max(subMax, tem);
}
max = Math.max(max, subMax);
}
return max;
}
On the other hand, Kadane's algorithm is much faster than the brute force approach because every maximum subarray is based on the previous result, and that's the reason why this problem belongs to dynamic programming.
而Kadane算法则是基于之前的计算结果来求最大值,如下所示,第6个元素所组成的最大值是第5个元素的最大值加自身计算出的,类似于阶乘的计算。
As you can see in the above picture, the addition of the 6th element is the maximum result from the 5th element which is 3 + 2. So, we could come up with this equation:
因此我们可以得出以下的公式:
The following code is the java version of Kadane's algorithm:
如下所示就是这个算法的Java实现:
public int maxSubArray(int[] nums) {
if(nums.length==1)
return nums[0];
int max = nums[0];
int subMax = nums[0];
for(int i=1;i<nums.length;i++)
{
subMax = Math.max(nums[i], subMax+nums[i]);
max = Math.max(max, subMax);
}
return max;
}
In conclusion, the brute force approach's time complexity is O(n^2), but Kadane's only O(n).
由此可见,常规的遍历算法时间复杂度为O(n^2),而Kadane算法则只有O(n).