238. 除自身以外数组的乘积
题目描述:
给你一个整数数组 nums,返回 数组 answer ,其中 answer[i] 等于 nums 中除 nums[i] 之外其余各元素的乘积 。
题目数据 保证 数组 nums之中任意元素的全部前缀元素和后缀的乘积都在 32 位 整数范围内。
请 不要使用除法,且在 O(n) 时间复杂度内完成此题。
示例 1:
输入: nums = [1,2,3,4]
输出: [24,12,8,6]
示例 2:
输入: nums = [-1,1,0,-3,3]
输出: [0,0,9,0,0]
提示:
- 2 <= nums.length <= 105
- -30 <= nums[i] <= 30
- 保证 数组 nums之中任意元素的全部前缀元素和后缀的乘积都在 32 位 整数范围内
进阶:你可以在 O(1) 的额外空间复杂度内完成这个题目吗?( 出于对空间复杂度分析的目的,输出数组 不被视为 额外空间。)
解题分析及思路:
方法:前缀和
思路:
对于某个位置 i ,其除自身以外数组的乘积 = 该元素左边所有元素乘积 * 该元素右边所有元素乘积
- 那么可以 以一个数组保存某个位置左边所有元素的乘积,即
L[i] = L[0] * L[1] * ... * L[i-1]
- 同样可以 以一个数组保存某个位置右边所有元素的乘积, 即
R[i] = L[i+1] * L[i+2] * ... L[n-1]
但是,这样空间复杂度就会是O(N),那么如何编程O(1)呢?
可以使用两个变量分别记录从左边的元素乘积和右边的元素乘积,并更新到结果集中。
也就是到位置 i 时,ans[i] = L[i] * R[i] = prefix * suffix
原数组: 1 2 3 4
左部分的乘积: 1 1 1*2 1*2*3
右部分的乘积: 2*3*4 3*4 4 1
结果: 1*2*3*4 1*3*4 1*2*4 1*2*3*1
结果: 24 12 1*2*4 1*2*3*1
func productExceptSelf(nums []int) []int {
n := len(nums)
ans := make([]int, n)
for i := range ans {
ans[i] = 1
}
prefix, suffix := 1, 1
for i := 0; i < n; i++ {
ans[i] *= prefix
ans[n-i-1] *= suffix
prefix *= nums[i]
suffix *= nums[n-i-1]
}
return ans
}
复杂度:
- 时间复杂度:O(N)
- 空间复杂度:O(1)
执行结果:
- 执行耗时:34 ms,击败了14.76% 的Go用户
- 内存消耗:8.1 MB,击败了10.55% 的Go用户