二叉树的遍历,非递归实现
- 前序遍历
//入栈时先是右子树再是左子树,即保证出栈时先是左子树再是右子树
//由于用的是栈数据结构所以先进后出先压右再压左,出的时候先出左再出右
public static void preOrderNoR(TreeNode root){
if(root==null){
return;
}
Stack<TreeNode> stack=new Stack<>();
stack.push(root);
while (!stack.empty()){
TreeNode cur=stack.pop();
if (cur.right!=null){
stack.push(cur.right);
}
if(cur.left!=null){
stack.push(cur.left);
}
System.out.print(cur.val);
}
}
- 中序遍历
//先是循环向左走一路压栈,再取栈顶元素访问,再从栈顶元素右子树出发
//进行找左循环上一步
public static void inOrderNoR(TreeNode root){
if(root==null){
return;
}
Stack<TreeNode> stack=new Stack<>();
TreeNode cur=root;
while (true) {
while(cur!=null){
stack.push(cur);
cur=cur.left;
}
if (stack.empty()){
break;
}
TreeNode top=stack.pop();
System.out.print(top.val);
cur=top.right;
}
}
3.后序遍历
public static void postOrderNoR(TreeNode root){
if(root==null){
return;
}
Stack<TreeNode> stack=new Stack<>();
TreeNode cur=root;
TreeNode pre=null;//访问过的前一个值
while(true){
//循环将左子树依次入栈
while(cur!=null){
stack.push(cur);
cur=cur.left;
}
if (stack.isEmpty()){
break;
}
TreeNode top=stack.pop();
//如果栈顶结点的右子树为空,直接访问
//如果右子树不为空,但是右子树已经被访问,进行访问
if(top.right==null || pre==top.right){
System.out.print(top.val);
stack.pop();
pre=top;
}else{
//右子树不为空,且右子树未被访问,继续进行循环入栈左子树
cur=top.right;
}
}
}