2023-09-24  阅读(9)
原文作者:moxiaolin 原文地址: https://blog.csdn.net/qq_37909508/article/details/90229417

题目描述

输入一棵二叉搜索树,将该二叉搜索树转换成一个排序的双向链表。要求不能创建任何新的结点,只能调整树中结点指针的指向。

    /**
    public class TreeNode {
        int val = 0;
        TreeNode left = null;
        TreeNode right = null;
    
        public TreeNode(int val) {
            this.val = val;
    
        }
    
    }
    */
    public class Solution {
        public TreeNode Convert(TreeNode pRootOfTree) {
            if(pRootOfTree==null)
                return null;
            if(pRootOfTree.left==null&&pRootOfTree.right==null)
                return pRootOfTree;
            // 1.将左子树构造成双链表,并返回链表头节点
            TreeNode left = Convert(pRootOfTree.left);
            TreeNode p = left;
            // 2.定位至左子树双链表最后一个节点
            while(p!=null&&p.right!=null){
                p = p.right;
            }
            // 3.如果左子树链表不为空的话,将当前root追加到左子树链表
            if(left!=null){
                p.right = pRootOfTree;
                pRootOfTree.left = p;
            }
            // 4.将右子树构造成双链表,并返回链表头节点
            TreeNode right = Convert(pRootOfTree.right);
            // 5.如果右子树链表不为空的话,将该链表追加到root节点之后
            if(right!=null){
                right.left = pRootOfTree;
                pRootOfTree.right = right;
            }
            return left!=null?left:pRootOfTree;  
        }
    }

遇到递归,就需要举例进行分析,不然你根本看不到递归在干嘛!

假设有如下一棵二叉搜索树:

202309242324041041.png

执行下面这段代码:

202309242324048682.png

一直到节点1停止,当前left=节点1:

202309242324056773.png

因为节点1没有右孩子,所以继续往下:

202309242324108464.png

将p的父节点pRootOfTree,加到p的右节点, 将p放到pRootOfTree左结点,这样就形成了双向链表;

当前双向链表的结构:

202309242324114695.png

继续往下

202309242324121096.png

节点6进入递归:

来到当前位置:

202309242324128547.png

节点6的左孩子节点4进入递归:

因为节点4没有左右孩子,返回节点4,left=节点4,由于节点4没有右孩子,执行到:

202309242324133738.png

将p的父节点pRootOfTree加到p的右孩子上面,将p 加到pRootOfTree的左孩子上面;

结构如下图所示:

202309242324140009.png

继续往下:

2023092423241464510.png

将pRootOfTree节点(6)的右孩子放入到递归中:

节点7没有左右孩子,直接返回节点7,right=节点7;

这样的话,就可以直接将节点7加入到双向链表中:

2023092423241515611.png

结构如下图所示:

2023092423241579212.png

继续往下

2023092423241633113.png

左结点left是4哦,这样别忘了,然后返回:

2023092423241686814.png

当前位置是left=1,pRootOfTree=3,(递归是真的有意思) ,到一下

2023092423241809715.png

将right加入链表中之后,的结构:

2023092423241858416.png 然后返回:

2023092423241936917.png

后面的代码我就我具体分析了,后面基本上就是将根结点加入到该左孩子链表的尾部,然后一样的方式去递归右孩子双向链表,把根结点放到链表头就可以了;

总结:递归是二叉树问题的核心,递归写起来简单,理解起来难,而且要一步步讲出来的话,越描述到下面,越难描述,所以后面我就没有继续描述了,因为递归中的一步步回归是真的麻烦.

永远要记住:不积跬步无以至千里!


Java 面试宝典是大明哥全力打造的 Java 精品面试题,它是一份靠谱、强大、详细、经典的 Java 后端面试宝典。它不仅仅只是一道道面试题,而是一套完整的 Java 知识体系,一套你 Java 知识点的扫盲贴。

它的内容包括:

  • 大厂真题:Java 面试宝典里面的题目都是最近几年的高频的大厂面试真题。
  • 原创内容:Java 面试宝典内容全部都是大明哥原创,内容全面且通俗易懂,回答部分可以直接作为面试回答内容。
  • 持续更新:一次购买,永久有效。大明哥会持续更新 3+ 年,累计更新 1000+,宝典会不断迭代更新,保证最新、最全面。
  • 覆盖全面:本宝典累计更新 1000+,从 Java 入门到 Java 架构的高频面试题,实现 360° 全覆盖。
  • 不止面试:内容包含面试题解析、内容详解、知识扩展,它不仅仅只是一份面试题,更是一套完整的 Java 知识体系。
  • 宝典详情:https://www.yuque.com/chenssy/sike-java/xvlo920axlp7sf4k
  • 宝典总览:https://www.yuque.com/chenssy/sike-java/yogsehzntzgp4ly1
  • 宝典进展:https://www.yuque.com/chenssy/sike-java/en9ned7loo47z5aw

目前 Java 面试宝典累计更新 400+ 道,总字数 42w+。大明哥还在持续更新中,下图是大明哥在 2024-12 月份的更新情况:

想了解详情的小伙伴,扫描下面二维码加大明哥微信【daming091】咨询

同时,大明哥也整理一套目前市面最常见的热点面试题。微信搜[大明哥聊 Java]或扫描下方二维码关注大明哥的原创公众号[大明哥聊 Java] ,回复【面试题】 即可免费领取。

阅读全文