2022-1-7二叉树day1

题1:

翻转一棵二叉树。

示例:

输入:

     4
   /   \
  2     7
 / \   / \
1   3 6   9

输出:

     4
   /   \
  7     2
 / \   / \
9   6 3   1

备注:
这个问题是受到 Max Howell 的 原问题 启发的 :

谷歌:我们90%的工程师使用您编写的软件(Homebrew),但是您却无法在面试时在白板上写出翻转二叉树这道题,这太糟糕了。
 1 /**
 2  * Definition for a binary tree node.
 3  * public class TreeNode {
 4  *     int val;
 5  *     TreeNode left;
 6  *     TreeNode right;
 7  *     TreeNode() {}
 8  *     TreeNode(int val) { this.val = val; }
 9  *     TreeNode(int val, TreeNode left, TreeNode right) {
10  *         this.val = val;
11  *         this.left = left;
12  *         this.right = right;
13  *     }
14  * }
15  */
16 class Solution {
17     public TreeNode invertTree(TreeNode root) {
18         if (root==null) return root;
19         TreeNode temp=null;
20         temp=root.left;
21         root.left=root.right;
22         root.right=temp;
23         invertTree(root.left);
24         invertTree(root.right);
25         return root;
26     }
27 }

递归,对于root节点,左右子树交换,再递归左右子树。

题2:

给定一个 完美二叉树 ,其所有叶子节点都在同一层,每个父节点都有两个子节点。二叉树定义如下:

struct Node {
  int val;
  Node *left;
  Node *right;
  Node *next;
}

填充它的每个 next 指针,让这个指针指向其下一个右侧节点。如果找不到下一个右侧节点,则将 next 指针设置为 NULL

初始状态下,所有 next 指针都被设置为 NULL

 

进阶:

  • 你只能使用常量级额外空间。
  • 使用递归解题也符合要求,本题中递归程序占用的栈空间不算做额外的空间复杂度。

 

示例:

输入:root = [1,2,3,4,5,6,7]
输出:[1,#,2,3,#,4,5,6,7,#]
解释:给定二叉树如图 A 所示,你的函数应该填充它的每个 next 指针,以指向其下一个右侧节点,如图 B 所示。序列化的输出按层序遍历排列,同一层节点由 next 指针连接,'#' 标志着每一层的结束。

 

提示:

  • 树中节点的数量少于 4096
  • -1000 <= node.val <= 1000
 1 /*
 2 // Definition for a Node.
 3 class Node {
 4     public int val;
 5     public Node left;
 6     public Node right;
 7     public Node next;
 8 
 9     public Node() {}
10     
11     public Node(int _val) {
12         val = _val;
13     }
14 
15     public Node(int _val, Node _left, Node _right, Node _next) {
16         val = _val;
17         left = _left;
18         right = _right;
19         next = _next;
20     }
21 };
22 */
23 
24 class Solution {
25     public Node connect(Node root) {
26         if (root==null) return root;
27         newconnect(root.left,root.right);
28         return root;
29     }
30 
31     public void newconnect(Node left,Node right){
32         if (left==null||right==null){
33             return;
34         }
35         left.next=right;
36         newconnect(left.left,left.right);
37         newconnect(right.left,right.right);
38         newconnect(left.right,right.left);
39     }
40 }

递归:光有root参数不够,因此新建一个递归函数,左子树的左右节点,右子树的左右节点,左右子树的右左节点。

题3:

给你二叉树的根结点 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]

 

提示:

  • 树中结点数在范围 [0, 2000] 内
  • -100 <= Node.val <= 100

 

进阶:你可以使用原地算法(O(1) 额外空间)展开这棵树吗?

 1 /**
 2  * Definition for a binary tree node.
 3  * public class TreeNode {
 4  *     int val;
 5  *     TreeNode left;
 6  *     TreeNode right;
 7  *     TreeNode() {}
 8  *     TreeNode(int val) { this.val = val; }
 9  *     TreeNode(int val, TreeNode left, TreeNode right) {
10  *         this.val = val;
11  *         this.left = left;
12  *         this.right = right;
13  *     }
14  * }
15  */
16 class Solution {
17     public void flatten(TreeNode root) {
18         if (root==null) return;
19         TreeNode right=root.right;
20         //临时变量记录右子树
21         root.right=root.left;
22         root.left=null;
23         //左子树变成null,右子树变成左子树
24         flatten(root.right);
25         //拉长左子树,因为左子树已经到了右子树上了,所以是root.right 
26         while (root.right!=null){
27             root=root.right;
28         }
29         //拉长后遍历到最后
30         //将右子树拼接上
31         root.right=right;
32         //把右子树也拉长
33         flatten(root.right);
34     }
35 }

递归思想,具体思路见注释。主要思想是利用递归拉长左子树和右子树。

posted on 2022-01-07 17:18  阿ming  阅读(31)  评论(0编辑  收藏  举报

导航