zoukankan      html  css  js  c++  java
  • 二叉树的最近公共祖先问题

    一、普通二叉树的公共祖先问题

    /**
     * Definition for a binary tree node.
     * struct TreeNode {
     *     int val;
     *     TreeNode *left;
     *     TreeNode *right;
     *     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
     * };
     */
    class Solution {
    public:
        TreeNode* lowestCommonAncestor(TreeNode* root, TreeNode* p, TreeNode* q) {
            //求最近公共祖先,如果可以自底向上搜索就好了,正好,后序遍历就是自底向上的,所以采用后序递归遍历框架
            //递归终止条件base case
            if(root == nullptr)
                return nullptr;
            if(root == p || root == q)
                return root;
            //要遍历整棵树,先把递归的结果存起来,下面进行逻辑处理
         //在递归函数有返回值的情况下,如果要搜索一条边,递归函数返回值不为空的时候,立刻返回,如果搜索整个树,直接用一个left、right接住返回值,这个left、right后续还有逻辑
          处理的需要,也就是后序遍历处理中间节点的逻辑。
    TreeNode* left = lowestCommonAncestor(root->left, p, q); TreeNode* right = lowestCommonAncestor(root->right, p, q); //如果p和q都在以root为根的树中,那么left好right一定是p和q(从base case得出) if(left != nullptr && right != nullptr) return root; //如果p和q都不在以root为根的树中 if(left == nullptr && right == nullptr) return nullptr; //剩下的就是q和q只有一个存在与以root为根的树中,函数返回该节点 return left == nullptr? right : left; } };

    二、二叉搜索树的公共祖先问题

    相比于普通二叉树,二叉搜索树有一些特性,可以利用这些特性来改善算法性能。

    因为二叉树搜索树的特性,其实只要从上到下遍历的时候,遍历的当前节点数值在[p,q]区间中说明该节点就是最近公共祖先了。

    /**
     * Definition for a binary tree node.
     * struct TreeNode {
     *     int val;
     *     TreeNode *left;
     *     TreeNode *right;
     *     TreeNode(int x) : val(x), left(NULL), right(NULL) {}
     * };
     */
    
    class Solution {
    public:
        TreeNode* lowestCommonAncestor(TreeNode* root, TreeNode* p, TreeNode* q) {
            //虽然按题意不会出现但还是判断一下吧养成一个良好的习惯
            if(root == nullptr)
                return root;
            //只搜索一条边,因为是二叉搜索树,如果在这条边中,找到后直接返回
            if(root->val > p->val && root->val > q->val) {
                TreeNode* left = lowestCommonAncestor(root->left, p, q);
                if(left != nullptr)
                    return left;
            }
            if(root->val < p->val && root->val < q->val) {
                TreeNode* right = lowestCommonAncestor(root->right, p, q);
                if(right != nullptr)
                    return right;
            }
            //剩下的几种情况就是root就在[p,q]区间里了,直接返回即可
            return root;
        }
    };
  • 相关阅读:
    [ARC 102D]All Your Paths are Different Lengths
    [NOI 2016] 优秀的拆分
    [TJOI 2015] 线性代数
    [LUOGU 4717] 快速沃尔什变换
    [NOI 2006] 最大获利
    Javascript继承机制的设计
    必应输入法产品分析
    你不得不知道的HTML5的新型标签
    Mobile Web
    10行代码爬取网页
  • 原文地址:https://www.cnblogs.com/masbay/p/14121223.html
Copyright © 2011-2022 走看看