53.最大子数组和
实现思路
- 定义一个数组
dp,其中dp[i]表示以nums[i]结尾的最大子数组和。 - 初始化
dp[0]为nums[0]。 - 从
i = 1开始遍历数组,对于每个位置i,有两种选择:- 以
nums[i]自身作为一个新的子数组的开始,即nums[i]。 - 将
nums[i]加入到以nums[i - 1]结尾的最大子数组中,即dp[i - 1] + nums[i]。
- 以
- 因此,状态转移方程为:
dp[i] = Math.max(nums[i], dp[i - 1] + nums[i])。 - 在计算
dp数组的同时,维护一个变量maxSum来记录当前的最大子数组和,最终返回maxSum。
代码实现
关键点
为什么比较 nums[i] 和 dp[i - 1] + nums[i]?
因为 dp[i] 的定义是:必须以 nums[i] 结尾的最大子数组和。
所以遍历到 nums[i] 时,只有两种选择:
- 从
nums[i]重新开始一个子数组,此时子数组和是nums[i]。 - 把
nums[i]接到前面的最大子数组后面,此时子数组和是dp[i - 1] + nums[i]。
因此需要比较:
如果 dp[i - 1] 是负数,继续加上它会拖累当前结果,就应该从 nums[i] 重新开始;如果 dp[i - 1] 是正数,接上前面的子数组会让结果更大。
一句话总结:对于以 nums[i] 结尾的最大子数组,要么从自己开始,要么接在前面的最大子数组后面,没有第三种情况。


