代码随想录算法训练营第21天|● 530.二叉搜索树的最小绝对差 ● 501.二叉搜索树中的众数 ● 236. 二叉树的最近公共祖先

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

题目链接:https://leetcode.cn/problems/minimum-absolute-difference-in-bst/

var getMinimumDifference = function(root) {
let res=Infinity
// pre为当前节点的前一个节点
let pre=null
// 采用中序遍历
const getMin=function(node){
    if(node===null) return
    // 左
    getMin(node.left)
    // 中
    if(pre!==null){
        res=Math.min(res,node.val-pre.val)
    }
    // 记录前一个节点
    pre=node
    // 右
    getMin(node.right)
}
getMin(root)
return res
};

解题思路:

1.本题要求的是求出最小绝对差,直白的想法是通过中序遍历把这些元素依次放入数组中,然后两两进行比较,将差值再放入一个新的数组中,最后返回最小差值。

2.但上述方法太过于麻烦并且得重新申请新的内存空间。定义两个变量,一个变量指向当前节点,另一个变量指向当前节点的前一个节点,这样两个数相减,依次向后操作,直到遍历完所有节点,每次都和前一次相减的结果作比较,最终返回最小值,且没有额外开辟新的内存空间。

501.二叉搜索树中的众数

题目链接:https://leetcode.cn/problems/find-mode-in-binary-search-tree/

var findMode = function(root) {
let pre=null,count=0,maxCount=0,res=[]
// cur为当前所遍历的元素
const getManyNums=function(cur){
    if(cur===null)return 
    // 中序遍历
    // 左
    getManyNums(cur.left)
    // 中
    if(pre===null){
        // pre为所遍历当前元素的前一个元素 为null的情况下说明刚遍历到第一个元素
        count=1
    }else if(pre.val===cur.val){
        count++
    }else{
        count=1
    }
    pre=cur
    if(count===maxCount){
        res.push(cur.val)
    }
    if(count>maxCount){
        maxCount=count
        res=[]
        res.push(cur.val)
    }
    // 右
    getManyNums(cur.right)
}
getManyNums(root)
return res
};

解题思路:

1.搜索二叉树中的众数,字面理解就是找出出现次数最多的数并且返回它即可。

2.其中count为单个元素所出现的频率,maxCount为所有元素中出现的最高频率,采用中序遍历的方法。这里有三个阶段,首先当pre=null的时候,即遍历到的元素为第一个,那么count则为一。其次当pre.val和cur.val的值相等的时候,那么让count++,统计出它们出现的次数。最后当不是这两种情况时,说明当前遍历的元素遇到了和前一个节点不一样的值,那么count重新赋值为1即可。

3.最重要的一点是很多人都认为需要把二叉树遍历两遍才能求出那个所有元素中出现频率最高的元素,实则不用。只需要在count>maxCount的时候,把maxCount的值更新,然后重新让当前值加入数组中返回即可。

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

题目链接:https://leetcode.cn/problems/lowest-common-ancestor-of-a-binary-tree/

var lowestCommonAncestor = function(root, p, q) {
    const getAnc=function(root,p,q){
        if(root===null) return root
        if(root===p||root===q) return root
        // 由于需要从下往上,所以使用后序遍历
        // 左
        let left=getAnc(root.left,p,q)
        // 右
        let right=getAnc(root.right,p,q)
        // 中
        // 左右子树都不为空的情况下
        if(left&&right) return root
        else if(left&&!right) return left
        else if(!left&&right) return right
        return null
    }
    return getAnc(root,p,q)
};

解题思路:

1.本题需要从下往上遍历,所以用到后序遍历。具体看代码注释即可,依旧采用的是递归遍历。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值