【力扣-二叉树】19、二叉搜索树的最近公共祖先(235)

「这是我参与11月更文挑战的第20天,活动详情查看:2021最后一次更文挑战

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

题目描述

给定一个二叉搜索树, 找到该树中两个指定节点的最近公共祖先。

百度百科中最近公共祖先的定义为:“对于有根树 T 的两个结点 p、q,最近公共祖先表示为一个结点 x,满足 x 是 p、q 的祖先且 x 的深度尽可能大(一个节点也可以是它自己的祖先)。”

例如,给定如下二叉搜索树:  root = [6,2,8,0,4,7,9,null,null,3,5]

 

示例 1:

输入: root = [6,2,8,0,4,7,9,null,null,3,5], p = 2, q = 8
输出: 6 
解释: 节点 2 和节点 8 的最近公共祖先是 6。
复制代码

示例 2:

输入: root = [6,2,8,0,4,7,9,null,null,3,5], p = 2, q = 4
输出: 2
解释: 节点 2 和节点 4 的最近公共祖先是 2, 因为根据定义最近公共祖先节点可以为节点本身。
复制代码

解析

自底向上查找就可以找到公共祖先了

    二叉树回溯的过程可以实现自底向上查找

    后序遍历就是天然的回溯过程,最先处理的一定是叶子节点

    如果找到一个节点,该节点的左子树上出现节点p ,右子树上出现节点q
    那么这个节点就是p q 的公共祖先


    递归三部曲
        1、确定递归函数的参数与返回值
            需要递归函数的返回值来确定是否找到了p 或 q节点
            那么返回值类型可以是bool类型
            但是还需要返回最近的公共节点,所以可以直接返回p 或 q 
            返回值不为空,就说明找到了 p 或 q
    
        2、确定终止条件
            如果遇到了节点p 或 q 或是NULL ,就直接返回

        3、单层递归的逻辑
            本题递归函数需要返回值,使用 left接左子树的递归结果,使用 right 接右子树的递归结果。

复制代码

代码

class Solution
{
public:
    TreeNode *lowestCommonAncestor(TreeNode *root, TreeNode *p.TreeNode *q)
    {
        if (root == p || root == q || root == NULL)
        {
            return root;
        }

        TreeNode *left = lowestCommonAncestor(root->left, p, q);
        TreeNode *right = lowestCommonAncestor(root->right, p, q);

        // 如果 left和right都不为空,则说明 root 就是最近的公共节点
        if (left != NULL && right != NULL)
        {
            return root;
        }
        // 如果 left 为空 right 不为空,则返回right
        else if (left == NULL && right != NULL)
        {
            return right;
        }
        // 如果 right 为空 left 不为空,则返回left

        else if (left != NULL && right == NULL)
        {
            return right;
        }
        else
        {
            return NULL;
        }
    }
};
复制代码

Guess you like

Origin juejin.im/post/7032931791845621797