AcWing 19 二叉树的下一个节点
发布日期:2021-05-28 16:30:10 浏览次数:28 分类:精选文章

本文共 1804 字,大约阅读时间需要 6 分钟。

找出二叉树节点在中序遍历序列中的后继节点是技术性的问题,需要对二叉树的结构和遍历特性有深入理解。以下从零开始详细分析解题思路,并提供最终优化后的代码实现。

首先,中序遍历的定义是:对于某个二叉树节点,从左子树访问完毕后,先访问该节点,最后访问右子树。所以,每个节点的后继节点可能是右子树的左most节点,或者父节点中的特定节点,具体情况因树的结构而异。

解题关键点分析

  • 节点存在右子树

    • 如果当前节点有右子树,则其中序遍历后的后继节点应是该右子树的最左边节点。因为中序遍历顺序为左子树根节点右子树按照左至右顺序访问,所以右子树的最左边节点是在根节点过程之后的最先被访问到的节点。
  • 缺少右子树

    • 当前节点没有右子树的情况下,该节点在中序遍历中的后继节点由其在父节点中的位置决定。若当前节点是父节点的左孩子,则其中序遍历后的父节点可能就是后继节点;若当前节点是父节点右孩子,则需要继续向上查找父节点的左孩子,直到找到一个节点或到达根节点。
    • 继续向上查找的逻辑实际上是回溯过程中的处理方式,因为在缺少右子树的情况下,后继节点只能在父节点或其上层节点电子之中找到。
  • 下面的代码实现将分两步骤处理:

  • 处理有右子树的情况

    • 递归或迭代的方式移动到右子树的最左节点,返回该节点。
  • 处理无右子树的情况

    • 逆向查找上层节点,找到是否是左孩子,若是,则当前父节点就是后继;否则,继续向上查找,直到找到父节点。
    • 最坏情况下,需要回到根节点,此时检查根节点是否是左孩子,若有左孩子,则返回根节点的左孩子。
  • 代码实现优化

    为了保证代码的可执行性和设定好的维护性,接下来提供一个清晰的代码模板:

    nodeTS {    val: number;    left: nodeTS | null;    right: nodeTS | null;    father: nodeTS | null;}class Solution {    inorderSuccessor(p: nodeTS): nodeTS | null {        // 如果存在右子树,则后继节点是右子树的左most节点        if (p.right) {            let current = p.right;            while (current.left) {                current = current.left;            }            return current;        }        // 如果没有右子树,则向上查找上层节点        // 找到第一个不作为右孩子的父节点        while (p && (p.father?.right === p)) {            p = p.father;        }        return p.father?.left ?? null;        // 需要注意的情况是,当p位于根节点的右侧时,它没有父亲的情况下,该函数如何处理    }}

    需要注意的是:

  • 当节点p在根节点的右侧,并且根节点的左孩子存在时,函数返回根节点的左孩子。

  • 如果根节点没有左孩子,则函数会返回null。

  • 终止条件应处理好,以免进入死循环。例如,当p是根节点时,在无右孩子的情况下,函数已经返回正确结果。

  • 前后验证

    我可以利用示例二叉树:

    2   / \  1   3

    验证函数的工作流程:

    • 对于节点2:

      • 检查右射子树是否存在,是的,进入右子树,移动到3的左节点,此时3没有左子树,返回3。
    • 对于节点1:

      • 检查右射子树不存在,开始猜上层节点:
        • 1是2的左子树,返回2。
    • 对于节点3:

      • 没有右子树,进入上层查找:
        • 3是2的右子树,
        • 继续向上到达根节点2,
        • 2不是左子树,但根节点的左子树存在,
        • 返回根节点的左子树节点1。

    那么测试情况显示函数是正确的。

    总结

    通过以下方法可以系统地解决该问题:

  • 分情况讨论,先有右子树的情况,再无右子树的情况。
  • 在有右子树的情况下,直接找到右子树的最左节点。
  • 在无右子树的情况下向上查找,直到找到父节点的最左子树节点或到达根节点。
  • 处理边界情况,例如根节点没有左孩子等情况。
  • 这个方法论在面对二叉树问题时,是解决遍历相关题意的通用方法,具有较好的扩展性和可维护性。

    上一篇:AcWing 20 用两个栈实现队列
    下一篇:2024年你必须阅读的15本网络安全书籍

    发表评论

    最新留言

    逛到本站,mark一下
    [***.202.152.39]2025年04月28日 09时19分22秒