代码随想录刷题day21 | 530.二叉搜索树的最小绝对差、501.二叉搜索树中的众数、236. 二叉树的最近公共祖先

530.二叉搜索树的最小绝对差

给你一个二叉搜索树的根节点 root ,返回 树中任意两不同节点值之间的最小差值 。
差值是一个正数,其数值等于两值之差的绝对值。

示例:
在这里插入图片描述
输入:root = [4,2,6,1,3]
输出:1

思路:中序遍历二叉搜索树(递增),每次计算当前节点与前一个节点的差值,更新最小值,更新前一个指针。

class Solution {
public:
    TreeNode* pre = nullptr;//前一个节点
    int minValue = INT_MAX;//最小绝对差
    void travasal(TreeNode* root){//中序遍历
        if(root == nullptr) return;
        
        travasal(root->left);
        if(pre != nullptr)
            minValue = min(minValue, root->val - pre->val);
        pre = root;
        travasal(root->right);
    }
    
    int getMinimumDifference(TreeNode* root) {
        travasal(root);
        return minValue;
    }
};

501.二叉搜索树中的众数

给你一个含重复值的二叉搜索树(BST)的根节点 root ,找出并返回 BST 中的所有 众数(即,出现频率最高的元素)。
如果树中有不止一个众数,可以按 任意顺序 返回。
假定 BST 满足如下定义:

  • 结点左子树中所含节点的值 小于等于 当前节点的值
  • 结点右子树中所含节点的值 大于等于 当前节点的值
  • 左子树和右子树都是二叉搜索树

思路
中序遍历二叉搜索树,指针pre记录上一个节点
每次遍历一个节点时,更新当前节点的频率,更新pre指针,更新最大频率,更新结果集
最后返回结果数组即可

class Solution {
public:
    int count = 0;//当前节点频率
    int maxCount = 0;//最大的频率
    TreeNode* pre = nullptr;//前一个节点
    vector<int> res;//结果集
    //中序遍历
    void travasal(TreeNode* cur){
        if(cur == nullptr) return;
        
        travasal(cur->left);//左
        if(pre == nullptr) count = 1;//第一个节点
        else if(pre->val == cur->val) count++;//节点值相等,count值+1
        else count = 1;//节点值不等,频率归1
        pre = cur;//更新前一个节点

        if(count == maxCount) res.push_back(cur->val); 
        if(count > maxCount){
            maxCount = count;
            res.clear();
            res.push_back(cur->val);
        }
        travasal(cur->right);//右
    }
    vector<int> findMode(TreeNode* root) {
        travasal(root);
        return res;
    }
};

236. 二叉树的最近公共祖先

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

示例
在这里插入图片描述
输入:root = [3,5,1,6,2,0,8,null,null,7,4], p = 5, q = 4
输出:5
解释:节点 5 和节点 4 的最近公共祖先是节点 5 。因为根据定义最近公共祖先节点可以为节点本身。

思路
后序遍历左右中可以将结果一层一层返回到根节点,实现从下到上的遍历,找到最近公共祖先

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);
        if(left != NULL && right != NULL) return root;
        if(left == NULL) return right;
        return left;     
    }
};

流程图帮助理解
在这里插入图片描述
总结

  1. 求最小公共祖先,需要从底向上遍历,那么二叉树,只能通过后序遍历(即:回溯)实现从低向上的遍历方式。
  2. 在回溯的过程中,必然要遍历整棵二叉树,即使已经找到结果了,依然要把其他节点遍历完,因为要使用递归函数的返回值(也就是代码中的left和right)做逻辑判断。
  3. 要理解如果返回值left为空,right不为空为什么要返回right,为什么可以用返回right传给上一层结果。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值