Leetcode热题100【第五周】完结篇!

【第五周打卡完成✔】

  • 一天不落的完成啦~
  • 后50%的题目明显感觉由于没有深入思考和总结套路而力不从心
  • 准备下周开始一轮复习并接入ACM模式的训练
#236.二叉树的最近公共祖先【二叉树】
class Solution:
    def lowestCommonAncestor(self, root: 'TreeNode', p: 'TreeNode', q: 'TreeNode') -> 'TreeNode':
        if not root or root == p or root == q:return root
        left = self.lowestCommonAncestor(root.left,p,q)
        right = self.lowestCommonAncestor(root.right,p,q)
        if not left:return right
        if not right:return left
        return root
        
#238.除自身以外数组的乘积【数组】
class Solution:
    def productExceptSelf(self, nums: List[int]) -> List[int]:
        ans,tmp = [1]*len(nums),1
        for i in range(1,len(nums)):
            ans[i] = ans[i-1]*nums[i-1]
        for i in range(len(nums)-2,-1,-1):
            tmp *= nums[i+1]
            ans[i] *= tmp
        return ans

#240.搜索二维矩阵II【矩阵】
class Solution:
    def searchMatrix(self, matrix: List[List[int]], target: int) -> bool:
        i,j = len(matrix)-1,0
        while i >= 0 and j <len(matrix[0]):
            if matrix[i][j] > target:i -= 1
            elif matrix[i][j] < target:j += 1
            else:return True
        return False
        
#279.完全平方数【动态规划】
class Solution:
    def numSquares(self, n: int) -> int:
        dp = [i for i in range(n+1)]
        for i in range(2,n+1):
            for j in range(1,int(i**(0.5))+1):
                dp[i] = min(dp[i],dp[i-j*j]+1)
        return dp[-1]

#283.移动零【双指针】
class Solution:
    def moveZeroes(self, nums: List[int]) -> None:
        j = 0 
        for i in range(len(nums)):
            if nums[i]:
                nums[i],nums[j] = nums[j],nums[i]
                j += 1

#287.寻找重复数【快慢指针】
class Solution:
    def findDuplicate(self, nums: List[int]) -> int:
        slow,fast = 0,0
        while True:
            slow = nums[slow]
            fast = nums[nums[fast]]
            if fast == slow:
                break
        find = 0
        while slow != find:
            slow = nums[slow]
            find = nums[find]
        return find

#300.最长递增子序列【动态规划】
class Solution:
    def lengthOfLIS(self, nums: List[int]) -> int:
        if not nums:return 0
        dp = [1]*len(nums)
        for i in range(len(nums)):
            for j in range(i):
                if nums[j] < nums[i]:
                    dp[i] = max(dp[i],dp[j]+1)
        return max(dp)

#309.买卖股票的最佳时机含冷冻期【动态规划】
class Solution:
    def maxProfit(self, prices: List[int]) -> int:
        n = len(prices)
        dp = [[0,0] for _ in range(n)]
        dp[0] = [-prices[0],0]
        for i in range(1,n):
            dp[i][0] = max(dp[i-1][0],-prices[i]+(dp[i-2][1] if i>1 else 0))
            dp[i][1] = max(dp[i-1][1],+prices[i]+dp[i-1][0])
        return dp[-1][-1]

#322.零钱兑换【动态规划】
class Solution:
    def coinChange(self, coins: List[int], amount: int) -> int:
        dp = [float('inf')]*(amount+1)
        dp[0] = 0
        for i in range(1,amount+1):
            for j in range(len(coins)):
                if coins[j] <= i:
                    dp[i] = min(dp[i],dp[i-coins[j]]+1)
        return dp[amount] if dp[amount] != float('inf') else -1

#337.打家劫舍III【动态规划】
class Solution:
    def rob(self, root: Optional[TreeNode]) -> int:
        def _rob(root):
            if not root:return 0,0
            left = _rob(root.left)
            right = _rob(root.right)
            v1 = root.val + left[1] +right[1]
            v2 = max(left)+max(right)
            return v1,v2
        return max(_rob(root))

#338.比特位计数【⭐】
class Solution:
    def countBits(self, n: int) -> List[int]:
        res = []
        for i in range(n+1):
            res.append(bin(i).count("1"))
        return res

#347.前K个高频元素【⭐】
class Solution:
    def topKFrequent(self, nums: List[int], k: int) -> List[int]:
        count = collections.Counter(nums)
        return [item[0] for item in count.most_common(k)]

#394.字符串解码【栈】
class Solution:
    def decodeString(self, s: str) -> str:
        stack,res,multi = [],"",0
        for c in s:
            if c == '[':
                stack.append([multi,res])
                res,multi = "",0
            elif c == ']':
                curr_multi,last_res = stack.pop()
                res = last_res + curr_multi * res
            elif '0' <= c <= '9':
                multi = multi *10 + int(c)
            else:
                res += c
        return res

#399.除法求值【图论】
class Solution:
    def calcEquation(self, equations: List[List[str]], values: List[float], queries: List[List[str]]) -> List[float]:
        graph = {}
        for (x,y),v in zip(equations,values):
            if x in graph:
                graph[x][y] = v
            else:
                graph[x] = {y:v}
            if y in graph:
                graph[y][x] = 1/v
            else:
                graph[y] = {x:1/v}
            
        def dfs(s,t) -> int:
            if s not in graph:
                return -1
            if t == s:
                return 1
            for node in graph[s].keys():
                if node == t:
                    return graph[s][node]
                elif node not in visited:
                    visited.add(node)
                    v = dfs(node,t)
                    if v != -1:
                        return graph[s][node] * v
            return -1
        
        res = []
        for qs,qt in queries:
            visited = set()
            res.append(dfs(qs,qt))
        return res

#406.根据身高重建队列【排序】
class Solution:
    def reconstructQueue(self, people: List[List[int]]) -> List[List[int]]:
        res = []
        people = sorted(people,key = lambda x:(-x[0],x[1]))
        for p in people:
            if len(res) <= p[1]:
                res.append(p)
            elif len(res) > p[1]:
                res.insert(p[1],p)
        return res

#416.分割等和子集【动态规划】
class Solution:
    def canPartition(self, nums: List[int]) -> bool:
        all_sum,N = sum(nums),len(nums)
        if all_sum%2 == 1:
            return False
        half_sum = all_sum // 2
        dp = [False] * (half_sum+1)
        dp[0] = True
        for i in range(len(nums)):
            for j in range(half_sum,nums[i] - 1,-1):
                dp[j] = dp[j] or dp[j -nums[i]]
        return dp[-1]

#437.路径总和III【前缀和】
class Solution:
    def pathSum(self, root: Optional[TreeNode], targetSum: int) -> int:
        def dfs(node,cnts,cursum):
            if not node:return 0
            cursum += node.val
            ans = cnts[cursum - targetSum]
            cnts[cursum] += 1
            if node.left:
                ans += dfs(node.left,cnts,cursum)
            if node.right:
                ans += dfs(node.right,cnts,cursum)
            cnts[cursum] -= 1
            return ans
        return dfs(root,Counter([0]),0)

#438.找到字符串中所有字母异位词【滑动窗口】
class Solution:
    def findAnagrams(self, s: str, p: str) -> List[int]:
        m,n = len(s),len(p)
        ans = []
        if m < n:
            return ans
        cnts_p = [0] * 26
        for c in p:
            cnts_p[ord(c) - ord('a')] += 1
        cur = [0] * 26
        for i in range(m):
            cur[ord(s[i]) - ord('a')] += 1
            if i >= n - 1:
                if cur == cnts_p:
                    ans.append(i - n + 1)
                cur[ord(s[i - n + 1]) -ord('a')] -= 1
        return ans

#448.找到所有数组中消失的数字【⭐】
class Solution:
    def findDisappearedNumbers(self, nums: List[int]) -> List[int]:
        counter = set(nums)
        N = len(nums)
        res = []
        for i in range(1,N+1):
            if i not in counter:
                res.append(i)
        return res

#461.汉明距离【⭐】
class Solution:
    def hammingDistance(self, x: int, y: int) -> int:
        return bin(x ^ y).count('1')

#494.目标和【动态规划】
class Solution:
    def findTargetSumWays(self, nums: List[int], target: int) -> int:
        target += sum(nums)
        if target < 0 or target % 2:
            return 0
        target //= 2
        n = len(nums)
        f = [[0] * (target + 1) for _ in range(n+1)]
        f[0][0] = 1
        for i,x in enumerate(nums):
            for c in range(target + 1):
                if c < x:
                    f[i+1][c] = f[i][c]
                else:
                    f[i+1][c] = f[i][c]+f[i][c-x]
        return f[n][target]

#538.把二叉搜索树转化为累加树【递归】
class Solution:
    def convertBST(self, root: Optional[TreeNode]) -> Optional[TreeNode]:
        s = 0
        def dfs(node):
            if node is None:
                return
            dfs(node.right)
            nonlocal s
            s += node.val
            node.val = s
            dfs(node.left)
        dfs(root)
        return root

#543.二叉树的直径【递归】
class Solution:
    def diameterOfBinaryTree(self, root: Optional[TreeNode]) -> int:
        self.ans = 1
        def depth(root):
            if not root:return 0
            L = depth(root.left)
            R = depth(root.right)
            self.ans = max(self.ans,L+R+1)
            return max(L,R) + 1
        depth(root)
        return self.ans - 1

#560.和为k的子数组【前缀和】
class Solution:
    def subarraySum(self, nums: List[int], k: int) -> int:
        num_times = collections.defaultdict(int)
        num_times[0] = 1
        cur_sum = 0
        res = 0
        for i in range(len(nums)):
            cur_sum += nums[i]
            if cur_sum - k in num_times:
                res += num_times[cur_sum - k]
            num_times[cur_sum] += 1
        return res

#581.最短无序连续子数组【双指针】
class Solution:
    def findUnsortedSubarray(self, nums: List[int]) -> int:
        new_nums = sorted(nums)
        left,right = 0,len(nums)-1
        while left < len(nums):
            if nums[left] != new_nums[left]:
                break
            left += 1
        if left == len(nums):
            return 0
        while right > left:
            if nums[right] != new_nums[right]:
                break
            right -= 1
        return right - left + 1

#617.合并二叉树【递归】
class Solution:
    def mergeTrees(self, root1: Optional[TreeNode], root2: Optional[TreeNode]) -> Optional[TreeNode]:
        if root1 is None:return root2
        if root2 is None:return root1
        return TreeNode(root1.val + root2.val,
                self.mergeTrees(root1.left,root2.left),
                self.mergeTrees(root1.right,root2.right))

#621.任务调度器【贪心算法】
class Solution:
    def leastInterval(self, tasks: List[str], n: int) -> int:
        ct = collections.Counter(tasks)
        nbucket = ct.most_common(1)[0][1]
        last_bucket_size = list(ct.values()).count(nbucket)
        res = (nbucket - 1)*(n+1)+last_bucket_size
        return max(res,len(tasks))

#647.回文子串【动态规划】
class Solution:
    def countSubstrings(self, s: str) -> int:
        dp = [[False] * len(s) for _ in range(len(s))]
        result = 0
        for i in range(len(s)-1,-1,-1):
            for j in range(i,len(s)):
                if s[i] == s[j]:
                    if j - i <= 1:
                        result += 1
                        dp[i][j] = True
                    elif dp[i+1][j-1]:
                        result += 1
                        dp[i][j] = True
        return result

#739.每日温度【单调栈】
class Solution:
    def dailyTemperatures(self, temperatures: List[int]) -> List[int]:
        n = len(temperatures)
        ans = [0] * n
        st = []
        for i in range(n-1,-1,-1):
            t = temperatures[i]
            while st and t >= temperatures[st[-1]]:
                st.pop()
            if st:
                ans[i] = st[-1] - i
            st.append(i)
        return ans
  • 2
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值