152. 乘积最大子数组
152. 乘积最大子数组
题目
Given an integer array nums
, find a subarray that has the largest product, and return the product.
The test cases are generated so that the answer will fit in a 32-bit integer.
Example 1:
Input: nums = [2,3,-2,4]
Output: 6
Explanation: [2,3] has the largest product 6.
Example 2:
Input: nums = [-2,0,-1]
Output: 0
Explanation: The result cannot be 2, because [-2,-1] is not a subarray.
Constraints:
1 <= nums.length <= 2 * 10^4
-10 <= nums[i] <= 10
- The product of any prefix or suffix of
nums
is guaranteed to fit in a 32-bit integer.
题目大意
给定一个整数数组 nums ,找出一个序列中乘积最大的连续子序列(该序列至少包含一个数)。
解题思路
- 给出一个数组,要求找出这个数组中连续元素乘积最大的值。
- 分情况讨论:
- 不和别人乘,就是 n 自己
- n 是负数,乘上前面的最小积
- n 是正数,乘上前面的最大积
- 这一题是 DP 的题,状态转移方程是:最大值是
Max(f(n)) = Max( Max(f(n-1)) * n, Min(f(n-1)) * n, n)
;最小值是Min(f(n)) = Min( Max(f(n-1)) * n, Min(f(n-1)) * n, n)
。只要动态维护这两个值,如果最后一个数是负数,最大值就在负数 _ 最小值和自己中产生,如果最后一个数是正数,最大值就在正数 _ 最大值和自己中产生。
代码
function maxProduct(arr) {
let res = arr[0];
let max = arr[0];
let min = arr[0];
let temp1, temp2;
for (let i = 1; i < arr.length; i++) {
// 先计算好,免得下面重复计算两次,结果会出错
temp1 = max * arr[i];
temp2 = min * arr[i];
max = Math.max(temp1, temp2, arr[i]);
min = Math.min(temp1, temp2, arr[i]);
res = Math.max(res, max);
}
return res;
}
相关题目
题号 | 标题 | 题解 | 标签 | 难度 |
---|---|---|---|---|
53 | 最大子数组和 | [✓] | 数组 分治 动态规划 | |
198 | 打家劫舍 | [✓] | 数组 动态规划 | |
238 | 除自身以外数组的乘积 | [✓] | 数组 前缀和 | |
628 | 三个数的最大乘积 | 数组 数学 排序 | ||
713 | 乘积小于 K 的子数组 | 数组 二分查找 前缀和 1+ |