返回

算法优化:235.二叉搜索树最近公共祖先的清晰解读

闲谈

二叉搜索树的最近公共祖先

在二叉搜索树中,最近公共祖先(Lowest Common Ancestor,简称LCA)是指两个节点在树中的最低公共祖先。换句话说,LCA是这两个节点的最近共同祖先,即它们在树中向上追溯能遇到的第一个公共节点。

算法实现

递归算法

递归算法是求解二叉搜索树最近公共祖先的最直接方法。它的思路是:

  1. 比较两个节点的值,如果它们相等,则它们就是彼此的最近公共祖先。
  2. 如果节点A的值小于节点B的值,则节点A的右子树和节点B都在节点A的右子树中,因此最近公共祖先一定在节点A的右子树中。
  3. 如果节点A的值大于节点B的值,则节点A的左子树和节点B都在节点A的左子树中,因此最近公共祖先一定在节点A的左子树中。
def lca(root, p, q):
    if root is None:
        return None

    if root.val == p.val or root.val == q.val:
        return root

    if root.val > p.val and root.val < q.val:
        return root

    if root.val > p.val and root.val > q.val:
        return lca(root.left, p, q)

    if root.val < p.val and root.val < q.val:
        return lca(root.right, p, q)

迭代算法

迭代算法也是一种求解二叉搜索树最近公共祖先的方法,它的思路是:

  1. 从根节点开始,依次访问每个节点。
  2. 如果当前节点的值大于两个节点的值,则最近公共祖先一定在当前节点的左子树中。
  3. 如果当前节点的值小于两个节点的值,则最近公共祖先一定在当前节点的右子树中。
  4. 如果当前节点的值等于两个节点的值,则当前节点就是最近公共祖先。
def lca(root, p, q):
    while root:
        if root.val > p.val and root.val > q.val:
            root = root.left
        elif root.val < p.val and root.val < q.val:
            root = root.right
        else:
            return root

算法分析

时间复杂度

递归算法和迭代算法的时间复杂度都是O(log n),其中n是二叉搜索树的节点数。这是因为这两种算法都是在二叉搜索树中进行深度优先搜索,而深度优先搜索的时间复杂度是O(log n)。

空间复杂度

递归算法的空间复杂度是O(log n),这是因为递归算法在调用自身时会产生栈空间。迭代算法的空间复杂度是O(1),这是因为它不需要使用栈空间。

算法应用

二叉搜索树的最近公共祖先算法在许多应用中都有着广泛的应用,例如:

  • 求解二叉搜索树中两个节点的距离
  • 求解二叉搜索树中两个节点的最近公共祖先
  • 求解二叉搜索树中两个节点之间的最长路径
  • 求解二叉搜索树中两个节点之间的最短路径

总结

二叉搜索树的最近公共祖先算法是一个重要的算法,它可以高效地找到两个节点在二叉搜索树中的最近公共祖先。该算法有两种实现方式:递归算法和迭代算法。这两种算法的时间复杂度都是O(log n),空间复杂度分别是O(log n)和O(1)。该算法在许多应用中都有着广泛的应用,例如:求解二叉搜索树中两个节点的距离、求解二叉搜索树中两个节点的最近公共祖先、求解二叉搜索树中两个节点之间的最长路径、求解二叉搜索树中两个节点之间的最短路径等。