返回

Python遍历:LeetCode 538. 将二叉搜索树转换为累加树

后端

问题

给定一个二叉搜索树 (BST),将其转换为累加树,使每个节点的值是原始节点值加上所有大于或等于该节点值的后继节点值之和。

Python 代码实现

def convertBST(root):
    total = 0

    def dfs(node):
        nonlocal total
        if not node:
            return

        # 逆序访问右子树
        dfs(node.right)

        # 将当前节点的值更新为累加值
        total += node.val
        node.val = total

        # 访问左子树
        dfs(node.left)

    dfs(root)
    return root

# 示例输入
root = TreeNode(5)
root.left = TreeNode(2)
root.right = TreeNode(13)
root.left.left = TreeNode(1)
root.left.right = TreeNode(3)
root.right.left = TreeNode(6)
root.right.right = TreeNode(15)

# 调用转换函数
convertBST(root)

# 打印转换后的累加树
def printTree(node):
    if not node:
        return

    print(node.val, end=" ")
    printTree(node.left)
    printTree(node.right)

printTree(root)

算法讲解

  1. 初始化变量 total: 我们使用一个名为 total 的变量来保存累加值。这个变量将在树的逆序遍历过程中不断更新。

  2. 定义 DFS 函数: 我们定义了一个辅助函数 dfs,它采用节点 node 作为参数,并使用深度优先搜索算法遍历树。

  3. 逆序访问右子树: 在函数 dfs 中,我们首先访问右子树。这是因为我们要将累加值添加到每个节点的值中,所以我们必须先访问大于或等于当前节点值的后继节点。

  4. 更新当前节点的值: 访问右子树后,我们将当前节点的值更新为累加值。

  5. 访问左子树: 更新当前节点的值后,我们访问左子树。这是因为我们要将累加值添加到每个节点的值中,所以我们必须访问小于或等于当前节点值的后继节点。

  6. 递归调用 dfs 函数: 我们在左子树和右子树上递归调用 dfs 函数,以遍历整个树。

  7. 返回转换后的树: 在遍历整个树之后,我们将转换后的累加树返回给调用者。

示例输入和输出

# 示例输入
root = TreeNode(5)
root.left = TreeNode(2)
root.right = TreeNode(13)
root.left.left = TreeNode(1)
root.left.right = TreeNode(3)
root.right.left = TreeNode(6)
root.right.right = TreeNode(15)

# 调用转换函数
convertBST(root)

# 打印转换后的累加树
def printTree(node):
    if not node:
        return

    print(node.val, end=" ")
    printTree(node.left)
    printTree(node.right)

printTree(root)

# 预期输出:
# 40 35 33 31 26 15 13 10 5

复杂度分析

  • 时间复杂度:该算法的时间复杂度为 O(n),其中 n 是树中的节点数。这是因为该算法遍历了树中的每个节点。
  • 空间复杂度:该算法的空间复杂度为 O(n),其中 n 是树中的节点数。这是因为该算法使用了递归调用,每个递归调用都需要存储一个栈帧。

总结

在本文中,我们讨论了如何使用 Python 将二叉搜索树转换为累加树。我们介绍了 DFS 算法并提供了详细的代码示例。我们还分析了算法的复杂度并提供了一个示例输入和输出。