最大子数组,Maximum Subarray, LeetCode题解(三)

Input: [-2,1,-3,4,-1,2,1,-5,4],
Output: 6
Explanation: [4,-1,2,1] has the largest sum = 6.

在一个数组里找一个连续的子数组,要求这个子数组的和最大。返回最大值。

这个问题必须用动态规划以及分治的思想来解。

先看最简单的问题:
(1). 假如数组长度只有1,从下标0开始,也就是数组为[-2], 那么此时最大子数组的和就是-2.
(2). 假如数组长度为2时,[-2, 1],要求这个数组的最大子数组,很明显最大子数组和是1,因为-2+1=-1, 算上前面的数,最终和是减小的,所以还不如舍弃上一步求出的-2,只取当前下标下的数字。

把上面两步做个推广:
(1). 怎么才能减小问题规模?肯定要通过递归。假如输入一个数组nums,起始位置0,终止位置len(nums)-1。那么每次调用都把数组长度减1,最后减到0,输入就是长度为1的数组,这个问题是有解的。
(2). 比较子问题,借助上一步求出来的,和当前问题进行比较,选出一个最大的。
class Solution(object):
    def maxSubArray(self, nums):
        """
        :type nums: List[int]
        :rtype: int
        """
        max_val = {"val": nums[0]}
        def inner_loop(nums, i, j, max_val):
            if i == j:
                return nums[i]
            tmp = max(nums[j], inner_loop(nums, i, j - 1, max_val) + nums[j])
            if tmp > max_val['val']:
                max_val['val'] = tmp
            return tmp
        inner_loop(nums, 0, len(nums) - 1, max_val)
        return max_val['val']

递归的思路,inner_loop(nums, i, j - 1, max_val) 这一步不断减少数组截止位置的下标。最后就能得到长度为1的数组的最大子数组。然后一步一步把后面的数字加进这个数组,长度为1时,为2时,为3时.......

这个问题不用递归更好,直接正向循环即可。

猜你喜欢

转载自www.cnblogs.com/importsober/p/13203861.html