二叉树展开为链表#
思路一:
维护一个全局指针 prev,表示已经处理好的部分的头节点。
按照 right -> left -> root 的顺序递归,这个是前序的逆序。
思路二:
原地 O(1) 空间,Morris
对于每个节点 cur
- 如果 cur.left 不为空
- 找到 cur.left 这颗子树的最右节点 pred
- pred.right = cur.right 把原右子树接到左子树最右端
- cur.right = cur.left
- cur.left = null
Java#
思路一:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
| class Solution {
private TreeNode prev = null;
public void flatten(TreeNode root) {
dfs(root);
}
// 反向前序:right -> left -> root
private void dfs(TreeNode node) {
if (node == null) return;
dfs(node.right);
dfs(node.left);
// 把当前节点接到已展开链表头(prev)前面
node.right = prev;
node.left = null;
prev = node;
}
}
|
思路三:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
| class Solution {
public void flatten(TreeNode root) {
TreeNode cur = root;
while (cur != null) {
if (cur.left != null) {
// 找到左子树的最右节点 pred
TreeNode pred = cur.left;
while (pred.right != null) {
pred = pred.right;
}
// 把原右子树接到 pred 的右边
pred.right = cur.right;
// 把左子树搬到右边,并清空左指针
cur.right = cur.left;
cur.left = null;
}
// 继续处理链表的下一个节点(始终沿 right 走)
cur = cur.right;
}
}
}
|