题目
输入的例子
思路
1.本题是一个分治的思想,我们找一个中间的值设为mid,最大子数组和的位置只可能有三种情况(下标从1开始):
- 全部在mid左边
1<=i<=mid - 全部在mid右边
mid+1<=i<=len(nums) - 跨过mid
i<=mid<j 即
i从mid开始向左
j从mid+1开始向右
2.递归
- 递归出口:只有一个元素的时候
if n==1
return nums[0]
- 递归中间过程:
max_left=self.maxSubArray(nums[0:len(nums)//2])
max_right=self.maxSubArray(nums[len(nums)//2:len(nums)])
3.计算跨过mid的最大子数组
max_l=nums[len(nums)//2-1]
tmp=0
for i in range(len(nums)//2-1,-1,-1)
tmp+=nums[i]
max_l=max(tmp,max_l)
max_r=nums[len(nums)//2]
tmp=0
for i in range(len(nums)//2,len(nums)):
tmp+=nums[i]
max_r=max(tmp,max_r)
代码
class Solution:
def maxSubArray(self,nums:List[int])->int:
n=len(nums)
if n==1:#递归终止条件
return nums[0]
else:#mid=len(nums//2)-1其实mid取其他值也行,要把mid包含进去
max_left=self.maxSubArray(nums[0:len(nums)//2])#递归计算左半边最大子序和
max_right=self.maxSubArray(nums[len(nums)//2:len(nums)])#递归计算左半边最大子序和
#计算中间的最大子序和,从中间开始向两边算起,保证从mid开始
max_l=nums[len(nums)//2-1]
tmp=0
for i in range(len(nums)//2-1,-1,-1):#range(start,stop,step)不包括stop
tmp+=nums[i]
max_l=max(tmp,max_l)
max_r=nums[len(nums)//2]
tmp=0
for i in range(len(nums)//2,len(nums)):
tmp+=nums[i]
max_r=max(tmp,max_r)
return max(max_right,max_left,max_l+max_r)