import java.util.ArrayList;
import java.util.LinkedList;
import java.util.Queue;
import java.util.Stack;
public class TraversingBinaryTree {
/*
* 1.前序遍历递归版
*/
public static void rePreTra(TreeNode root, ArrayList<Integer> list) {
if (root != null){
list.add(root.val);//先加根节点,再加左右子节点
rePreTra(root.left, list);
rePreTra(root.right, list);
}
}
/*
* 2.中序遍历递归版
*/
public static void reInTra(TreeNode root, ArrayList<Integer> list) {
if (root != null){
rePreTra(root.left, list);//先加左节点,再加根节点,再加右节点
list.add(root.val);
rePreTra(root.right, list);
}
}
/*
* 3.后序遍历递归版
*/
public static void rePostTra(TreeNode root, ArrayList<Integer> list) {
if (root != null){
rePreTra(root.left, list);//先加左节点,再加右节点,再加根节点
rePreTra(root.right, list);
list.add(root.val);
}
}
/*
* 4.前序遍历非递归版
* 首先,如果当前元素不为空,先记录下当前元素,然后入栈该元素,并依次类推其左节点;
* 如果遇到当前元素为空,则说明栈顶元素不存在左节点,则接着对其右节点做相同的工作即可;
*/
public static void preTra(TreeNode root, ArrayList<Integer> list) {
Stack<TreeNode> stack = new Stack<TreeNode>();
while (root != null || stack.size() > 0){
while (root != null){
list.add(root.val);//先记下节点,在将节点入栈
stack.push(root);
root = root.left;
}
if (stack.size() > 0){
root = stack.pop().right;
}
}
}
/*
* 5.中序遍历非递归版
* 首先,如果当前节点不为空,则先将当前节点入栈,接着查看它的左节点;
* 如果节点为空,且栈不为空,说明栈顶元素没有左节点,先记录栈顶元素,然后在判断该元素是否存在右节点,
* 若存在,则重复上述过程,若不存在,则继续出栈;
*/
public static void inTra(TreeNode root, ArrayList<Integer> list) {
Stack<TreeNode> stack = new Stack<TreeNode>();
while (root != null || stack.size() > 0){
while (root != null){
stack.push(root);
root = root.left;
}
if (stack.size() > 0){
root = stack.pop();
list.add(root.val); //与前序遍历的区别
root = root.right;
}
}
}
/*
* 6.后序遍历非递归版,稍显有些复杂,主要是多了一个临时节点来存储上一个被记录的节点
*/
public static void postTra(TreeNode root, ArrayList<Integer> list) {
Stack<TreeNode> stack = new Stack<TreeNode>();
TreeNode pre = root;
while (root != null || stack.size() > 0){
while (root != null){
stack.push(root);
root = root.left;
}
if (stack.size() > 0){
TreeNode temp = stack.peek().right;//栈顶元素的右节点,注意没有出栈
if (temp == null || temp == pre){ //temp == pre说明该节点右节点已经记录,可以记录根节点了
root = stack.pop();
list.add(root.val);
pre = root;
root = null;
} else {
root = temp;//temp不为空,说明该节点存在右节点,需要对右节点重复上面的过程
}
list.add(root.val); //与前序遍历的区别
root = root.right;
}
}
}
/*
* 7.层次遍历,使用辅助队列来实现,在节点出队列的同时,将其左右节点分别入队。
*/
public static void levelTra(TreeNode root, ArrayList<Integer> list) {
if (root == null)
return;
Queue<TreeNode> queue = new LinkedList<TreeNode>();
queue.add(root);
while (queue.size() > 0){
root = queue.poll();
list.add(root.val);
if (root.left != null)
queue.add(root.right);
if (root.right != null)
queue.add(root.right);
}
}
}
二叉树遍历
最新推荐文章于 2024-01-27 15:36:29 发布