标签:
https://oj.leetcode.com/problems/flatten-binary-tree-to-linked-list/
Given a binary tree, flatten it to a linked list in-place.
For example,
Given
1 / 2 5 / \ 3 4 6
The flattened tree should look like:
1 2 3 4 5 6
If you notice carefully in the flattened tree, each node‘s right child points to the next node of a pre-order traversal.
解题思路:
这题是很靠思路的一题。看似很难,解决后再考虑也不复杂。看看上面的例子,能看出来,操作是一个递归的过程。就是把每个子树的左侧子树,放到当前右子树的上面。然后把之前的右子树接在现在右子树的最右侧节点的右边。这个操作是可以preorder,inorder,postorder任意的。
也就是说,原来的二叉树,第一步可以做下面任意一步。
先flatten根节点,也就是preorder
1
\
2
/ \
3 4
\
5
\
6
或者先flatten左子树,也就是inorder
1
/ \
2 5
\ \
3 6
\
4
或者postorder。
下面代码是preorder的一个例子,可以调整
flatten(root.left);
flatten(root.right);
两行代码的顺序,最后处理的结果是一样的。
/** * Definition for binary tree * public class TreeNode { * int val; * TreeNode left; * TreeNode right; * TreeNode(int x) { val = x; } * } */ public class Solution { public void flatten(TreeNode root) { if(root == null){ return; } TreeNode right = root.right; if(root.left != null){ root.right = root.left; root.left = null; TreeNode temp = root; //temp为root原左子树(先右子树)的最右侧节点 while(temp.right != null){ temp = temp.right; } //将root原来的右子树接在temp的右侧 temp.right = right; } flatten(root.left); flatten(root.right); } }
上面是一个递归的方法,下面考虑如何改为迭代。我们可以看到,如果preorder处理的话,根节点的左侧子树直接都被甩到右侧了,那么left==null。这样完全可以preorder处理,然后root=root.right,直到root == null。迭代的代码如下。
/** * Definition for binary tree * public class TreeNode { * int val; * TreeNode left; * TreeNode right; * TreeNode(int x) { val = x; } * } */ public class Solution { public void flatten(TreeNode root) { //root===null的处理也可以省略 if(root == null){ return; } while(root != null){ TreeNode right = root.right; if(root.left != null){ root.right = root.left; root.left = null; TreeNode temp = root; //temp为root原左子树(先右子树)的最右侧节点 while(temp.right != null){ temp = temp.right; } //将root原来的右子树接在temp的右侧 temp.right = right; } root = root.right; } } }
这样我们可以看到,即便在preorder的递归方法下,flatten(root.left)的递归也是多余的,因为flatten完左子树,左子树一定是null的,直接回return。故代码可以间接为下面。
/** * Definition for binary tree * public class TreeNode { * int val; * TreeNode left; * TreeNode right; * TreeNode(int x) { val = x; } * } */ public class Solution { public void flatten(TreeNode root) { if(root == null){ return; } TreeNode right = root.right; if(root.left != null){ root.right = root.left; root.left = null; TreeNode temp = root; while(temp.right != null){ temp = temp.right; } temp.right = right; } // flatten(root.left); flatten(root.right); } }
从上面画的图想,会更容易理解。postorder就不能省略。
这道题对递归的考察和传统的遍历不太一样,又很像,确实比较考察对递归理解的是否深刻。需要好好掌握。
Flatten Binary Tree to Linked List
标签:
原文地址:http://www.cnblogs.com/NickyYe/p/4315810.html