leetcode 152:给你一个整数数组 nums ,请你找出数组中乘积最大的连续子数组(该子数组中至少包含一个数字),并返回该子数组所对应的乘积。
示例 1:
输入: [2,3,-2,4]
输出: 6
解释: 子数组 [2,3] 有最大乘积 6。
分析:题目求最大乘积,同样,用a[n]表示数组,用dp[i]表示乘积值
1.dp[i]最大,dp[i]=dp[i-1]*a[i],则要求dp[i-1]乘a[n]最大;因为a[i]有正负数之分,当a[i]>0,则求dp[i-1]最大;当a[i]<0,则求dp[i-1]最小
2.变形一下,将dp[i]一维数组升级成二维数组,dp[i][2], 第二维表示正负数,0表示正数,1表示负数,dp[i]永远是求最大值;
则 a[i]>0时,dp[i][0]=dp[i-1][0]*a[i],dp[i-1][0]正数最大值;当a[i]<0时,dp[i][0]=dp[i-1][1]*a[i],dp[i-1][1]负数最小值
则 a[i]>0时,dp[i][1]=dp[i-1][1]*a[i],dp[i-1][1]负数最小值;当a[i]<0时,dp[i][1]=dp[i-1][0]*a[i],dp[i-1][0]正数最大值
......
层层递推,最终递推到dp[1][1]、dp[1][0]和dp[0][1]、dp[0][0],而这些初始状态是已知的。
代码部分
1 public int maxProduct(int[] nums) { 2 int len = nums.length; 3 if (len == 0) { 4 return 0; 5 } 6 int[][] dp = new int[len][2]; 7 dp[0][0] = nums[0]; 8 dp[0][1] = nums[0]; 9 for (int i = 1; i < len; i++) { 10 if (nums[i] >= 0) { 11 dp[i][0] = Math.max(nums[i], nums[i] * dp[i - 1][0]); 12 dp[i][1] = Math.min(nums[i], nums[i] * dp[i - 1][1]); 13 } else { 14 dp[i][0] = Math.max(nums[i], nums[i] * dp[i - 1][1]); 15 dp[i][1] = Math.min(nums[i], nums[i] * dp[i - 1][0]); 16 } 17 } 18 19 int maxResult = dp[0][1]; 20 for (int i = 1; i < len; i++) { 21 maxResult = Math.max(maxResult, dp[i][0]); 22 } 23 System.out.println("乘积最大:"+maxResult); 24 return maxResult; 25 }