(1) 二叉树的遍历 (递归过程具体可以参考大话数据结构)
是指 :从根节点出发 ,按照某种次序访问所有结点 ,使得每个结点 被访问到 且只访问一次
//前序遍历
public static void preOrder(TreeNode root){
if(root == null){//递归出口
return;
}
System.out.println(root.data);
preOrder(root.left);
preOrder(root.right);
}
//中序遍历
public static void inOrder(TreeNode root){
if(root == null){//递归出口
return;
}
//左根右
inOrder(root.left);
System.out.print(root.data+" ");
inOrder(root.right);
}
//后序遍历
public static void afterOrder(TreeNode root){
if(root == null){//递归出口
return;
}
//左右根
afterOrder(root.left);
afterOrder(root.right);
System.out.print(root.data+ "");
}
(2)非递归形式实现(主要是后序遍历实现)
// 更详细地可以看这一篇 http://blog.sina.com.cn/s/blog_e3734cfe0102xfpn.html
//=========下面是非递归形式遍历=====
public static void preOrder2(TreeNode root){
//利用栈==先入后出 根左右 //先打印根节点
//先 new 一个栈
//节点不为空 , 打印,压栈 找到其左孩子 并且将其设置为当前节点
// 当前左孩子为空 进行弹栈 获得pop() ,然后将pop设置成他的右孩子
// 当前 右孩子为空,则进行弹栈, 获得pop,再设置pop设置成他的右孩子
Stack<TreeNode> stack =new Stack<>();
while(root != null || !stack.isEmpty()){
while(root != null){
System.out.print(root.data + " ");
stack.push(root);
root = root.left;
}
if(!stack.isEmpty()){
root = stack.pop();
root =root.right;
}
}
}
public static void inOrder2(TreeNode node){
Stack<TreeNode> stack =new Stack<>();
while(node != null || !stack.isEmpty()){
while(node != null){
stack.push(node);
node = node.left;
}
if(!stack.isEmpty()){
node =stack.pop();
System.out.print(node.data+" ");
node=node.right;
}
}
}
//后序遍历
public static void afterOrder2(TreeNode root){
if(root == null){
return;
}
Stack<TreeNode> stack = new Stack<>();
TreeNode pre= null; //当前节点之前访问的节点//
TreeNode cur;
stack.push(root);
while(!stack.isEmpty()){
cur = stack.peek();//获得栈顶元素
//当前节点 是叶子节点 可以直接访问该节点
//节点pre 不为空 且是当前节点的孩子
if((cur.left == null && cur.right == null)
|| (pre !=null) &&( pre==cur.left || pre==cur.right)){
System.out.println(cur.data);
stack.pop();
pre = cur;
}else{//当前节点是栈顶元素 如果当前节点 不是叶子节点 访问的也不是孩子节点
if(cur.right != null){
stack.push(cur.right);
}
if(cur.left !=null){
stack.push(cur.left);
}
}
}
(3)下面是完整的代码
/** 测试的树是这样的
* A
* / \
* B F
* \ \
* C G
* / \ /
* D E H
public class TreeNode {
String data;
TreeNode left;
TreeNode right;
public TreeNode(String val){
this.data = val;
this.left=null;
this.right=null;
}
}
import java.util.Stack;
public class Test {
//前序遍历
public static void preOrder(TreeNode root){
if(root == null){//递归出口
return;
}
System.out.println(root.data);
preOrder(root.left);
preOrder(root.right);
}
//中序遍历
public static void inOrder(TreeNode root){
if(root == null){//递归出口
return;
}
//左根右
inOrder(root.left);
System.out.print(root.data+" ");
inOrder(root.right);
}
//后序遍历
public static void afterOrder(TreeNode root){
if(root == null){//递归出口
return;
}
//左右根
afterOrder(root.left);
afterOrder(root.right);
System.out.print(root.data+ "");
}
//=========下面是非递归形式遍历=====
public static void preOrder2(TreeNode root){
//利用栈==先入后出 根左右 //先打印根节点
//先 new 一个栈
//节点不为空 , 打印,压栈 找到其左孩子 并且将其设置为当前节点
// 当前左孩子为空 进行弹栈 获得pop() ,然后将pop设置成他的右孩子
// 当前 右孩子为空,则进行弹栈, 获得pop,再设置pop设置成他的右孩子
Stack<TreeNode> stack =new Stack<>();
while(root != null || !stack.isEmpty()){
while(root != null){
System.out.print(root.data + " ");
stack.push(root);
root = root.left;
}
if(!stack.isEmpty()){
root = stack.pop();
root =root.right;
}
}
}
public static void inOrder2(TreeNode node){
Stack<TreeNode> stack =new Stack<>();
while(node != null || !stack.isEmpty()){
while(node != null){
stack.push(node);
node = node.left;
}
if(!stack.isEmpty()){
node =stack.pop();
System.out.print(node.data+" ");
node=node.right;
}
}
}
//后序遍历
public static void afterOrder2(TreeNode root){
if(root == null){
return;
}
Stack<TreeNode> stack = new Stack<>();
TreeNode pre= null; //当前节点之前访问的节点//
TreeNode cur;
stack.push(root);
while(!stack.isEmpty()){
cur = stack.peek();//获得栈顶元素
//当前节点 是叶子节点 可以直接访问该节点
//节点pre 不为空 且是当前节点的孩子
if((cur.left == null && cur.right == null)
|| (pre !=null) &&( pre==cur.left || pre==cur.right)){
System.out.println(cur.data);
stack.pop();
pre = cur;
}else{//当前节点是栈顶元素 如果当前节点 不是叶子节点 访问的也不是孩子节点
if(cur.right != null){
stack.push(cur.right);
}
if(cur.left !=null){
stack.push(cur.left);
}
}
}
}
public static void main(String[] args) {
TreeNode A = new TreeNode("A");
TreeNode B = new TreeNode("B");
TreeNode C = new TreeNode("C");
TreeNode D = new TreeNode("D");
TreeNode E = new TreeNode("E");
TreeNode F = new TreeNode("F");
TreeNode G = new TreeNode("G");
TreeNode H = new TreeNode("H");
A.left = B;
A.right = F;
B.left =null;
B.right=C;
C.left=D;
C.right=E;
F.left=null;
F.right=G;
G.left=H;
G.right=null;
preOrder(A);
System.out.println("===========");
afterOrder2(A);
System.out.println("=============");
inOrder2(A);
}
}