53、最大子序和
基本思想:
贪心算法
具体实现:
1.遍历nums,用count累积子序和
2.count加上nums[i]以后,count变为负数的话
从nums[i+1]开始从0累积count
3.result记录最大子序和
代码:
class Solution { public int maxSubArray(int[] nums) { if (nums.length == 1){ return nums[0]; } //自动拆箱 int result = Integer.MIN_VALUE;//int类型的最小值的常量可取的值为-2^31 int count = 0; for (int i = 0; i < nums.length; i++){ count += nums[i]; // 取区间累计的最大值(相当于不断确定最大子序终止位置) result = Math.max(result, count); //// 相当于重置最大子序起始位置,因为遇到负数一定是拉低总和 if (count < 0){ count = 0; } } return result; } }
基本思想:
动态规划
具体实现:
1.确定dp数组以及下标的含义
dp[i]:包括下标i之前的最大连续子序列和为dp[i]。
2.确定递推公式
dp[i]只有两个方向可以推出来:
- dp[i - 1] + nums[i],即:nums[i]加入当前连续子序列和
- nums[i],即:从头开始计算当前连续子序列和
取最大的,所以dp[i] = max(dp[i - 1] + nums[i], nums[i]);
3.dp数组初始化
递推公式中dp[i]依赖于dp[i - 1]的状态,dp[0]就是递推公式的基础。
4.确定遍历顺序
递推公式中dp[i]依赖于dp[i - 1]的状态,需要从前向后遍历。
5.举例推导dp数组
代码:
class Solution { public int maxSubArray(int[] nums) { if (nums.length == 0) return 0; int res = nums[0]; int[] dp = new int[nums.length]; dp[0] = nums[0]; for (int i= 1; i < nums.length; i++) { dp[i] = Math.max(dp[i - 1] + nums[i], nums[i]); res = res > dp[i] ? res : dp[i]; } return res; } }