【python3】leetcode 238. Product of Array Except Self (Medium)

238. Product of Array Except Self (Medium) 

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].

Example:

Input:  [1,2,3,4]
Output: [24,12,8,6]

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.)

1 space O(1),time O(n), 但使用了division ,先计算了所有不是0的乘积

这道题的corner case主要考虑0,1个0和多个0,

如果有多个0,那乘积就算排除自己也是0,

如果只有1个0,那如果自己是0,乘积就不是0

如果没有0,就要除自己

class Solution:
    def productExceptSelf(self, nums):
        """
        :type nums: List[int]
        :rtype: List[int]
        """
        product = []
        if not nums:return []
        allpro = 1
        zeronum = 0
        for i in nums:
            if i==0:zeronum+=1
            else:allpro *= i
        for i in range(len(nums)):
            if zeronum > 1:product.append(0)
            elif zeronum == 1 and nums[i]!=0:product.append(0)
            elif zeronum == 1 and nums[i]==0:
                product.append(allpro)
            else:#no zero
                product.append(int(allpro/nums[i]))
        return product

1 space O(1),time O(n),  不使用division: two pointers

 返回一个新list:prod

prod[i] = nums[0] * nums[1] *...*nums[i - 1] nums[i+1]*...*nums[len-1]

           = 该数左边乘积 * 该数右边乘积

| 0 |1 | 2|...| i - 1| i | i+1| ...| len-1|

left ——>           |         <——right

         <——right |   left ——>     

right                                        left

使用left和right指针 ,left从左往右扫描 ,right从右往左扫描

left扫描到的位置计算前面的乘积并记录到prod里 ; right扫描到的位置计算后面的乘积记录到prod里

这样的话刚开始两个都是各自计算无交集,等到left和right走到一半并各自继续扫描时,

这时候prod右半边是已经计算过右乘积的,prod左半边是已经计算过左乘积的,

left往右半边继续走,并把左乘积乘上prod[i] (<--这个prod[i]已经是右边乘积),得到左乘积*右乘积,同理right

知道left和right各自走到底,此时左右乘积均计算完毕。

注意 pord初始化为1,长度与nums同,因为prod[0] 没有左乘积,prod[len-1]没有右乘积,所以初始化为1 ,prod[0]乘以右乘积和prod[len-1]乘以左乘积时才会不变

class Solution:
    def productExceptSelf(self, nums):
        """
        :type nums: List[int]
        :rtype: List[int]
        """
        prod = [1]*len(nums)
        left = 0;right = len(nums)-1
        prodleft , prodright = nums[left],nums[right]
        while(left < len(nums)-1):
            prod[left + 1] *= prodleft
            prod[right - 1] *= prodright
            prodleft *= nums[left+1]
            prodright *= nums[right-1]
            left += 1
            right -= 1
        return prod

更直观一点是扫描2边,一次left扫描到右边,一次right扫描到左边,

        prod = [1]*len(nums)
        left = 0
        prodleft = nums[left]
        while(left < len(nums)-1):
            prod[left+1] *= prodleft
            prodleft *= nums[left+1]
            left += 1
        right = len(nums)-1
        prodright =  nums[right]
        while(right >0):
            prod[right - 1] *= prodright
            prodright *= nums[right -1]
            right -= 1
        return prod

 

你可能感兴趣的:(leetcode,python)