144. Binary Tree Preorder Traversal
前序遍历
Given a binary tree, return the preorder traversal of its nodes' values.
For example:
Given binary tree {1,#,2,3}
,
1
\
2
/
3
return [1,2,3]
.
Note: Recursive solution is trivial, could you do it iteratively?
递归
public List<Integer> preorderTraversal(TreeNode root) {
List<Integer> list = new ArrayList<>();
if (root == null)
return list;
preorder(root, list);
return list;
}
private void preorder(TreeNode root, List<Integer> list) {
if (root != null) {
list.add(root.val);
preorder(root.left, list);
preorder(root.right, list);
}
迭代
public List<Integer> preorderTraversal(TreeNode root) {
List<Integer> list = new ArrayList<>();
if (root == null)
return list;
Stack<TreeNode> stack = new Stack<>();
stack.push(root);
while (!stack.isEmpty()) {
//出栈
TreeNode node=stack.pop();
list.add(node.val);
//访问右子树
if(node.right!=null)
stack.push(node.right);
//左子树
if(node.left!=null)
stack.push(node.left);
}
return list;
}
94. Binary Tree Inorder Traversal
中序遍历
Given a binary tree, return the inorder traversal of its nodes' values.
For example:
Given binary tree [1,null,2,3]
,
1
\
2
/
3
return [1,3,2]
.
Note: Recursive solution is trivial, could you do it iteratively?
递归
public List<Integer> inorderTraversal(TreeNode root) {
List<Integer> list = new ArrayList<>();
if (root == null)
return list;
inorder(root, list);
return list;
}
private void inorder(TreeNode root, List<Integer> list) {
if (root != null) {
inorder(root.left, list);
list.add(root.val);
inorder(root.right, list);
}
}
迭代
public List<Integer> inorderTraversal(TreeNode root) {
List<Integer> list = new ArrayList<>();
if (root == null)
return list;
Stack<TreeNode> stack = new Stack<>();
while (root != null || !stack.isEmpty()) {
if (root != null) {
stack.push(root);
root = root.left;
} else {
root = stack.pop();
list.add(root.val);
root = root.right;
}
}
return list;
}
145. Binary Tree Postorder Traversal
后序遍历
Given a binary tree, return the postorder traversal of its nodes' values.
For example:
Given binary tree {1,#,2,3}
,
1
\
2
/
3
return [3,2,1]
.
Note: Recursive solution is trivial, could you do it iteratively?
递归
public List<Integer> postorderTraversal(TreeNode root) {
List<Integer> list = new ArrayList<>();
if (root == null)
return list;
postorder(root, list);
return list;
}
private void postorder(TreeNode root,
List<Integer> list) {
if (root != null) {
postorder(root.left, list);
postorder(root.right, list);
list.add(root.val);
}
}
迭代
关键点是找一个flag存储刚刚访问过的结点
public List<Integer> postorderTraversal(TreeNode root) {
List<Integer> list = new ArrayList<>();
if (root == null)
return list;
TreeNode p = root;
Stack<TreeNode> stack = new Stack<>();
// 辅助指针用于标记最近访问的结点,
// 标记是从左子树返回还是右子树返回
TreeNode flag = null;
while (p != null || !stack.isEmpty()) {
if (p != null) {
// 走到最左边
stack.push(p);
p = p.left;
}
// 向右
else {
// 去栈顶结点
p = stack.peek();
// 若右子树存在且未被访问过
if (p.right != flag && p.right != null) {
// 转向右
p = p.right;
stack.push(p);
// 在走到最左
p = p.left;
} else {
// 访问
p = stack.pop();
list.add(p.val);
// 记录最近访问的结点
flag = p;
// 结点访问完毕后重置指针p
p = null;
}
}
}
return list;
}