代码随想录算法训练营二刷第11天 | 合并二叉树、二叉搜索树中的搜索

617.合并二叉树

题目要求 按位置 合并两个二叉树。

分析:这个题目如果用层序遍历,那么需要用一个值去代替每一个空值,也就是位置不好定,做起来肯定麻烦!因此,优先用递归的前序遍历!遍历的方法按照递归3部曲进行即可。

本题对于递归思想进行一下总结和理解:

  • 因为树是一种递归结构,你可以理。解为:树是由一颗颗树构成的!构成树 的树称为子树。因此,在我们合并两个子树的过程中,我们的思路应该是这样的:
    1. 首先合并两颗树的两个根节点
    2. 其次合并两颗树的两个左节点(而合并两个左节点的过程,其实就是合并两个左子树的两个根节点的过程,因此就是将两个左子树进行合并,合并函数就是过程1中的函数)。
    3. 然后合并两颗树的两个右节点(而合并两个右节点的过程,其实就是合并两个 右子树的两个根节点 的过程,因此就是将两个右子树进行合并,合并函数就是过程1中的函数)。
  • 因此,就形成了一种递归思想,即:处理树的子树/子节点(左子树/右子树、左节点/右节点)的过程其实是和处理 树/根节点的过程、函数(方法)是一样一样的!
  • 最后根据上述的思想去考虑递归函数所需要传入的参数、返回值等,就清晰得多啦!

700.二叉搜索树中的搜索

二叉搜索树是一个有序树:

  • 若它的左子树不空,则左子树上所有结点的值均小于它的根结点的值;
  • 若它的右子树不空,则右子树上所有结点的值均大于它的根结点的值;
  • 它的左、右子树也分别为二叉搜索树

本题可以用递归法进行遍历,方法按照递归3部曲,不难!

想重点记录的是如何用迭代法对二叉树进行搜索

对于二叉搜索树可就不一样了,因为二叉搜索树的特殊性,也就是节点的有序性,可以不使用辅助栈或者队列就可以写出迭代法。

对于一般二叉树,递归过程中还有回溯的过程,例如走一个左方向的分支走到头了,那么要调头,在走右分支。

对于二叉搜索树,不需要回溯的过程,因为节点的有序性就帮我们确定了搜索的方向。

class Solution {
public:
    TreeNode* searchBST(TreeNode* root, int val) {
        while (root != NULL) {
            if (root->val > val) root = root->left;
            else if (root->val < val) root = root->right;
            else return root;
        }
        return NULL;
    }
};

98.验证二叉搜索树

要知道中序遍历下,输出的二叉搜索树节点的数值是有序序列。

有了这个特性,验证二叉搜索树,就相当于变成了判断一个序列是不是递增的了。

可以把二叉树转变为数组来判断,是最直观的!

这道题目比较容易陷入两个陷阱:

  • 陷阱1

不能单纯的比较左节点小于中间节点,右节点大于中间节点就完事了

写出了类似这样的代码:

if (root->val > root->left->val && root->val < root->right->val) {
    return true;
} else {
    return false;
}

我们要比较的是 左子树的 所有节点小于中间节点,右子树所有节点大于中间节点。所以以上代码的判断逻辑是错误的。

后面就是正常的递归3部曲:

注意递归函数要有bool类型的返回值, 我们在二叉树:递归函数究竟什么时候需要返回值,什么时候不要返回值? (opens new window)中讲了,只有寻找某一条边(或者一个节点)的时候,递归函数会有bool类型的返回值

其实本题是同样的道理,我们在寻找一个不符合条件的节点(某一特性),如果没有找到这个节点就遍历了整个树,如果找到不符合的节点了,立刻返回。

总结:验证二叉搜索树这道题用的是双指针的思路!

 

  • 7
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值