Grind75第2天 | 238.除自身以外数组的乘积、75.颜色分类、11.盛最多水的容器

发布时间:2024年01月07日

238.除自身以外数组的乘积

题目链接:https://leetcode.com/problems/product-of-array-except-self

解法:

这个题有follow up, 要求优化到空间复杂度为O(1),所以给出baseline和follow up的解法。

Baseline:利用索引左侧所有数字的乘积和右侧所有数字的乘积(即前缀与后缀)相乘得到答案。因此需要两个列表:L 和 R,对于nums中的索引i,L[i] 表示索引i左侧所有数字的乘积,R[i] 表示索引i右侧所以数字的乘积,那么L[i] *?R[i] 就是除自身以外数组的乘积。

空间复杂度为O(n)

Follow up:根据表格的主对角线(全为?1?),可将表格分为?上三角?和?下三角?两部分。分别迭代计算下三角和上三角两部分的乘积。

空间复杂度为O(1)

参考题解:上三角和下三角

边界条件:无

时间复杂度:O(n)

空间复杂度:

# 空间复杂度 O(n)
class Solution:
    def productExceptSelf(self, nums: List[int]) -> List[int]:
        length = len(nums)
        L, R = [1] * length, [1] * length
        res = [1] * length

        for i in range(1, length):
            L[i] = L[i-1] * nums[i-1]
        
        for i in range(length-2, -1, -1):
            R[i] = R[i+1] * nums[i+1]

        for i in range(length):
            res[i] = L[i] * R[i]

        return res
# 空间复杂度 O(1)
class Solution:
    def productExceptSelf(self, nums: List[int]) -> List[int]:
        length = len(nums)
        res = [1] * length
        temp = 1

        for i in range(1, length):
            res[i] = res[i-1] * nums[i-1]
        
        for i in range(length-2, -1, -1):
            temp *= nums[i+1]
            res[i] *= temp

        return res

75.颜色分类

题目链接:https://leetcode.com/problems/sort-colors

解法:

注意这个题要求原地修改,还有follow up要求只能扫描一次。

Baseline:baseline的解法是统计0,1,2三个元素的个数,然后在原数组中修改。需要扫描两次。

Follow up:这种写法大致思路是明白,但是实现的细节真的很容易出错。一会再总结。

边界条件:无

时间复杂度:O(n)

空间复杂度:O(1)

# baseline
class Solution:
    def sortColors(self, nums: List[int]) -> None:
        """
        Do not return anything, modify nums in-place instead.
        """
        count = [0] * 3
        for i in nums:
            count[i] += 1
        
        for i in range(len(nums)):
            if i < count[0]:
                nums[i] = 0
            elif i < count[0] + count[1]:
                nums[i] = 1
            else:
                nums[i] = 2
# 扫描一次
class Solution:
    def sortColors(self, nums: List[int]) -> None:
        """
        Do not return anything, modify nums in-place instead.
        """
        length = len(nums)
        if length < 2:
            return

        zero = 0
        two = length
        i = 0
        # 遵循左闭右开的写法
        while i < two:
            if nums[i] == 0:
                nums[i], nums[zero] = nums[zero], nums[i]
                zero += 1
                i += 1
            elif nums[i] == 1:
                i += 1
            else:
                two -= 1
                nums[i], nums[two] = nums[two], nums[i]

11.盛最多水的容器

题目链接:https://leetcode.com/problems/container-with-most-water

解法:

这个题用双指针。基本的思路是,双指针为i和j,容器的盛水量由短板决定 min(h[i], h[j]) * (j - i)。双指针从两端往中间移动,移动的过程中,(j - i)一定是变小的,那么为了得到更大的容积,就需要短板变大,所以只能移动短板。到两个指针相遇时,停止。

参考题解:双指针

边界条件:无

时间复杂度:O(n)

空间复杂度:O(1)

class Solution:
    def maxArea(self, height: List[int]) -> int:
        i, j, res = 0, len(height) - 1, 0
        while i < j:
            if height[i] < height[j]:
                res = max(res, height[i] * (j - i))
                i += 1
            else:
                res = max(res, height[j] * (j - i))
                j -= 1
        return res
文章来源:https://blog.csdn.net/Jack199274/article/details/135422243
本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。