Leetcode学习笔记 二叉搜索树BST

二叉搜索树-

简介-2

验证二叉搜索树,中等

注意:不是左子节点和右子节点需要符合,而是左子树和右子树需要符合,所以递归函数需要引入上下界
方法一,递归:

class Solution:
    def isValidBST(self, root: TreeNode) -> bool:
        if not root:
            return True
        def fct(node, low, high):
            if not node:
                return True
            if node.val >= high or node.val <= low:
                return False
            return fct(node.left,low,node.val) and fct(node.right,node.val,high)
        return fct(root , -math.inf, math.inf)

方法二,中序遍历:

class Solution:
    def isValidBST(self, root: TreeNode) -> bool:
        if not root:
            return True
        inorder = []
        def dfs(node,inorder):
            if not node:
                return True
            a = dfs(node.left,inorder)
            if not a:
                return False
            if not inorder or node.val > inorder[-1]:	# not inorder 要写在前面,否则会数组越界
                inorder.append(node.val)
            else:
                return False
            b = dfs(node.right,inorder)
            return b
        return dfs(root,inorder)   

二叉搜索树迭代器,中等
说不清楚,看代码吧
等于说模拟了一个递归的过程

class BSTIterator:

    def __init__(self, root: TreeNode):
        self.stack = []
        self.add_left_order(root)

    def add_left_order(self,node):
        while node:
            self.stack.append(node)
            node = node.left

    def next(self) -> int:
        smallestnode = self.stack.pop()
        if smallestnode.right:
            self.add_left_order(smallestnode.right)
        return smallestnode.val

    def hasNext(self) -> bool:
        return len(self.stack) > 0

BST中的基本操作

二叉搜索树中的搜索,简单
递归:

class Solution:
    def searchBST(self, root: TreeNode, val: int) -> TreeNode:
        if not root:
            return None
        if root.val == val:
            return root
        if root.val > val:
            return self.searchBST(root.left,val)
        return self.searchBST(root.right ,val)

迭代:

class Solution:
    def searchBST(self, root: TreeNode, val: int) -> TreeNode:
        while root:
            if root.val == val:
                return root
            if root.val > val:
                root = root.left
            else:
                root = root.right
        return None

二叉搜索树中的插入操作,中等
简单的迭代:

class Solution:
    def insertIntoBST(self, root: TreeNode, val: int) -> TreeNode:
        if not root:
            return TreeNode(val)
        node = root
        while node:
            lastnode = node
            if node.val > val:
                node = node.left
            else:
                node = node.right
        if lastnode.val > val:
            lastnode.left = TreeNode(val)
        else:
            lastnode.right = TreeNode(val)
        return root

删除二叉搜索树中的节点,中等
没搜到的不用删
官解用递归做
自己写的,嗯讨论,很长:

class Solution:
    def deleteNode(self, root: TreeNode, key: int) -> TreeNode:
        def connect(father,child,isleft):
            if isleft:
                father.left = child
            else:
                father.right = child
        
        dummy = TreeNode(0,root)
        node = root
        lastnode = dummy
        leftflag = True
        while node:
            if node.val == key:
                break
            elif node.val > key:
                lastnode = node
                node = node.left
                leftflag = True
            else:
                lastnode = node
                node = node.right
                leftflag = False
        #如果没找到值为key的节点,不用删除
        if not node:
            return dummy.left
        if not node.left and not node.right:
            connect(lastnode,None,leftflag)
        elif node.left and node.right:
            nextnode = node.right
            nextlastnode = None
            while nextnode.left:
                nextlastnode = nextnode            
                nextnode = nextnode.left
            if not nextlastnode: #补充的情况
                nextnode.left = node.left
                connect(lastnode,nextnode,leftflag)
                return dummy.left
            if not nextnode.right:
                nextlastnode.left = None
            else:
                nextlastnode.left = nextnode.right
            nextnode.left = node.left
            nextnode.right = node.right
            connect(lastnode,nextnode,leftflag)
        elif node.left:
            connect(lastnode,node.left,leftflag)
        else:
            connect(lastnode,node.right,leftflag)
        return dummy.left

小结-3

数据流中的第K大元素,简单
维护一个k个元素的最小堆,初始为k个负无穷
用列表即可,用下标的关系来维护父子关系

class KthLargest:

    def __init__(self, k: int, nums: List[int]):
        self.heap = [-math.inf for _ in range(k)]
        self.k = k
        for item in nums:
            self.add(item)

    def add(self, val: int) -> int:
        if val <= self.heap[0]:
            return self.heap[0]
        self.heap[0] = val
        i,son = 0,1
        while son < self.k:
            if son + 1 < self.k and self.heap[son] >= self.heap[son+1]:
                if val > self.heap[son+1]:
                    self.heap[i] = self.heap[son+1]
                    self.heap[son+1] = val
                    i = son+1
                    son = i*2+1
                else:
                    break
            else:
                if val > self.heap[son]:
                    self.heap[i] = self.heap[son]
                    self.heap[son] = val
                    i = son
                    son = i*2+1
                else:
                    break
        return self.heap[0]

二叉搜索树的最近公共祖先,简单
很简单,利用BST的性质,从根开始搜,第一个值在两个数之间的就是最近公共祖先

class Solution:
    def lowestCommonAncestor(self, root: 'TreeNode', p: 'TreeNode', q: 'TreeNode') -> 'TreeNode':
        if not root:
            return root
        if q.val < p.val:
            return self.lowestCommonAncestor(root,q,p)
        node = root
        while node:
            if node.val > q.val:
                node = node.left
            elif node.val < p.val:
                node = node.right
            else:
                return node

存在重复元素III,中等
用桶来做,时间复杂度O(n)

class Solution:
    def containsNearbyAlmostDuplicate(self, nums: List[int], k: int, t: int) -> bool:
        bucket = {}
        depth = t+1	#用t+1作为桶的宽度
        n = len(nums)
        for i in range(n):
            bucket_num = nums[i] // depth	#放入一个桶里
            if bucket_num in bucket:
                return True
            if bucket_num-1 in bucket and abs(bucket[bucket_num-1]-nums[i]) <= t:	#查前一个桶里有没有
                return True
            if bucket_num+1 in bucket and abs(bucket[bucket_num+1]-nums[i]) <= t:	#查后一个桶里有没有
                return True
            bucket[bucket_num] = nums[i]
            if i >= k:
                #del bucket[(nums[i-k]) // depth]
                bucket.pop(nums[i-k]//depth)
        return False

附录:平衡二叉搜索树-2

平衡二叉树,简单
自顶向下递归:O(n²)

class Solution:
    def countdepth(self,root):
        if not root:
            return 0
        return max(self.countdepth(root.left),self.countdepth(root.right)) + 1
    def isBalanced(self, root: TreeNode) -> bool:
        if not root:
            return True
        if abs(self.countdepth(root.left)-self.countdepth(root.right)) > 1:
            return False
        return self.isBalanced(root.left) and self.isBalanced(root.right)

自底向上对高度递归:O(n)

class Solution:
    def isBalanced(self, root: TreeNode) -> bool:
        def height(root):
            if not root:
                return 0
            leftheight = height(root.left)
            rightheight = height(root.right)
            if leftheight < 0 or rightheight < 0 or abs(leftheight-rightheight) > 1:
                return -1
            return max(leftheight,rightheight) + 1
        return not height(root) < 0

将有序数组转换为二叉搜索树,简单
递归,自己写的代码很简洁:

class Solution:
    def sortedArrayToBST(self, nums: List[int]) -> TreeNode:
        if not nums:
            return None
        n = len(nums)
        x = n // 2
        node = TreeNode(nums[x])
        node.left = self.sortedArrayToBST(nums[0:x])
        node.right = self.sortedArrayToBST(nums[x+1:n])
        return node

你可能感兴趣的:(LeetCode学习笔记)