算法--二叉树展开
Leetcode 114:
给你二叉树的根结点 root
,请你将它展开为一个单链表:
- 展开后的单链表应该同样使用
TreeNode
,其中right
子指针指向链表中下一个结点,而左子指针始终为null
。 - 展开后的单链表应该与二叉树 先序遍历顺序相同。
示例 1:
输入:root = [1,2,5,3,4,null,6] 输出:[1,null,2,null,3,null,4,null,5,null,6]
示例 2:
输入:root = [] 输出:[]
示例 3:
输入:root = [0] 输出:[0]
展开的顺序是二叉树的先序遍历的顺序。 把左子树不断的插入到右子树,原来的右子树放嫁接过来的左子树的最右边。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | public void flatten(TreeNode root) { while (root != null ) { //左子树为 null,直接考虑下一个节点 if (root.left == null ) { root = root.right; } else { // 找左子树最右边的节点 TreeNode pre = root.left; while (pre.right != null ) { pre = pre.right; } //将原来的右子树接到左子树的最右边节点 pre.right = root.right; // 将左子树插入到右子树的地方 root.right = root.left; root.left = null ; // 考虑下一个节点 root = root.right; } } } |
考虑把左子树嫁接到右子树,让原来的右子树接到左子树最后。不断的递归最终完成先序遍历的同时完成了单链表的构建。
1 2 | if (root.left == null ) { root = root.right;<br>考虑root当前的左子树是否为 null ,如果为 null ,就只能遍历右边。根节点出发,左子树没有,右子树也可能出现需要把右子树的左孩子拼到右侧的情况<br><br> |
1 2 3 4 5 | // 找左子树最右边的节点 TreeNode pre = root.left; while (pre.right != null ) { pre = pre.right; } <br>在这里,保存左子树的节点pre. 如果左子树有右孩子,就保存左子树的右孩子为pre。 这里保留pre是为了让root节点的右子树拼到root节点的左子树的后面。 |
1 2 3 | <br> //将原来的右子树接到左子树的最右边节点 pre.right = root.right; // 将左子树插入到右子树的地方 |
右子树拼到左子树的pre节点(要连接root右子树的节点)的右孩子节点。
root.right = root.left;
1 2 3 | <em id= "__mceDel" >左子树插入到右子树的地方,这时候,右子树的节点断开。<br><br>root.left = null ;<br>清空右子树的节点。<br> // 考虑下一个节点。root节点的下一个右节点作为root节点依次递归下去。 root = root.right;</em> |
分类:
算法
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 终于写完轮子一部分:tcp代理 了,记录一下
· 震惊!C++程序真的从main开始吗?99%的程序员都答错了
· 别再用vector<bool>了!Google高级工程师:这可能是STL最大的设计失误
· 单元测试从入门到精通
· 【硬核科普】Trae如何「偷看」你的代码?零基础破解AI编程运行原理