问题描述
Given an array nums of n integers where n > 1, return an array output such that output[i] is equal to the product of all the elements of nums except nums[i].
Constraint: It's guaranteed that the product of the elements of any prefix or suffix of the array (including the whole array) fits in a 32 bit integer.
Note: Please solve it without division and in O(n).
Follow up:
Could you solve it with constant space complexity? (The output array does not count as extra space for the purpose of space complexity analysis.)
给定一个有n个整数的数组,其中n个>为1,返回一个数组输出,使得输出[i]等于除了nums[i]之外的所有nums元素的乘积。
约束:保证数组的任何前缀或后缀(包括整个数组)的元素的乘积符合32位整数。
注意:请用O(n)代替除法求解。
跟进:
你能不能用常数空间复杂度来解它?(为了分析空间复杂性,输出数组不算作额外的空间。)
举例
输入: [1,2,3,4]
输出: [24,12,8,6]
Python 实现
实现一:除法。
很直接的思路,先把所有元素的乘积计算出来,然后分别除以每个元素就能得到相应的结果(虽然这不是题目要求的解法),其中需要特别考虑到, 当元素值为 0 时的处理。全程遍历了两次列表,除去 output 这个列表所占的空间,这个过程的时间复杂度为 O(N),空间复杂度为 O(1)。
class Solution(object):
def productExceptSelf(self, nums):
"""
:type nums: List[int]
:rtype: List[int]
"""
# Method 1: Division.
product = 1
output = []
zero_cnt = 0
for num in nums:
if num != 0:
product *= num
else:
zero_cnt += 1
for i in range(len(nums)):
if nums[i] == 0:
if zero_cnt == 1:
output.append(product)
else:
output.append(0)
else:
if zero_cnt != 0:
output.append(0)
else:
output.append(product/nums[i])
return output
解法二
同样是遍历两次列表,但是这个解法是先从左到右遍历一次,再从右到左遍历一次。其中第一次遍历时,依次计算出到当前元素为止,前面所有元素的乘积;第二次遍历则把除自身以外的其他右边的元素乘上,从而得到最终的结果。下面的表格可以帮助理解(为了更好的表示,我用字母abcdefg代表各个元素的乘积)。
index | 0 | 1 | 2 | 3 | 4 | 5 | 6 | 备注 |
nums | a | b | c | d | e | f | g | |
output (第一次遍历) | 1 | a | ab | abc | abcd | abcde | abcdef | 从左到右 |
right_product | bcdefg | cdefg | defg | efg | fg | g | 1 | 从右到左 |
output (第二次遍历) = output (第一次遍历) * right_product | bcdefg | acdefg | abdefg | abcefg | abcdfg | abcdeg | abcdef |
class Solution(object):
def productExceptSelf(self, nums):
"""
:type nums: List[int]
:rtype: List[int]
"""
# Method 2.
n = len(nums)
output = [1]
# Product of the first n-1 elements (from left to right).
for i in range(n-1):
output.append(nums[i]*output[i])
# Multiply the left rest elements (from right to right).
right_product = nums[-1]
for i in range(n-1, 0, -1):
output[i-1] *= right_product
right_product *= nums[i-1]
return output
链接:https://leetcode.com/problems/product-of-array-except-self/