遍历二叉树、恢复二叉树(java代码实现)

目录

遍历二叉树

前序遍历(DLR,根左右)

中序遍历(LDR,左根右)

后序遍历(LRD,左右根)

层次遍历

广度优先

深度优先

恢复二叉树

前序+中序

后序+中序

扫描二维码关注公众号,回复: 14708222 查看本文章

二叉树遍历代码实现


遍历二叉树

前序遍历(DLR,根左右)

(1)访问根结点。

(2)先序遍历根结点的左子树。

(3)先序遍历根结点的右子树。

中序遍历(LDR,左根右)

(1)先序遍历根结点的左子树。

(2)访问根结点。

(3)先序遍历根结点的右子树。

后序遍历(LRD,左右根)

(1)先序遍历根结点的左子树。

(2)先序遍历根结点的右子树。

(3)访问根结点。

层次遍历

从根结点开始,逐层自上而下遍历。当一层结点访问完后接着访问下一层,先遇到的结点先访问。

(1)将根结点入队,从对头取出一个元素,每取一个元素执行(2)。

(2)访问该元素所指结点。

(3)若该元素所指结点的左、右孩子结点非空,则将该元素所指结点的左孩子指针和右孩子指针依次入队。

(4)重复步骤(3),直到队空为止。

广度优先

深度优先

恢复二叉树

前序+中序

步骤:

(1)由前序序列获知根结点,然后根据中序序列确定左、右子树。

(2)由确定的左、右子树根据前序序列分别找出左、右子树的根结点,并把左、右子树的根结点连接到父结点。

(3)分别对左、右子树实行步骤(1)和(2),直到子树只剩下1个结点或2个结点或空为止。

前序:A C B R S E D F M L K

中序:R B S C E A F D L K M

1、   前序:A  C B R S E  D F M L K

                   根     左子树       右子树

         中序:R B S C E  A  F D L K M

                      左子树     根   右子树

2、   前序:C  B R S  E                                                  前序: F  M L K

                   根 左子树 右子树                                                    根 左子树 右子树

         中序:R B S  C  E                                                  中序:F  D  L K M

                  左子树 根 右子树                                              左子树  根 右子树

3、......

后序+中序

步骤:

(1)由后序序列获知根结点,然后根据中序序列确定左、右子树。

(2)由确定的左、右子树根据后序序列分别找出左、右子树的根结点,并把左、右子树的根结点连接到父结点。

(3)分别对左、右子树实行步骤(1)和(2),直到子树只剩下1个结点或2个结点或空为止。

中序:C B E D A G H F J I

后续:C E D B H G J I F A

1、   后序:C E D B  H G J I F  A

                    左子树    右子树     根

         中序:C B E D  A  G H F J I

                    左子树   根    右子树

2、   后序:C  E D  B                                                 后序: H G  J I  F

           左子树 右子树  根                                               左子树 右子树  根 

         中序:C  B  E D                                                 中序:G H  F  J I

           左子树  根  右子树                                                 左子树  根 右子树

3、......

二叉树遍历代码实现

import java.util.ArrayDeque;
import java.util.Arrays;
import java.util.LinkedList;

//树遍历
public class BinaryTree {	
	//一、声明节点
	public static class TreeNode{
		public int val;
		public TreeNode lchild;
		public TreeNode rchild;
		public TreeNode(int x){this.val=x;}
	}
	
	//二、构造二叉树  递归构造
	public static TreeNode createBinaryTree(LinkedList<Integer> list) {
		TreeNode node = null;
		//出口
		if(list.isEmpty()) return null;

		//创建节点
		Integer val = list.pollFirst();
		//Integer val = list.removeFirst();
		//递归构造
		if(val!=null) {
			node = new TreeNode(val);
			
			node.lchild = createBinaryTree(list);
			node.rchild = createBinaryTree(list);
		}
		
		return node;
	}
	
	//三、二叉树遍历
	//1、先序遍历 递归
	public static void preOrderTraversal(TreeNode node) {
		//出口
		if(node==null) return;
		
		//输出当前节点
		System.out.print(node.val + " ");
		//继续遍历
		preOrderTraversal(node.lchild);
		preOrderTraversal(node.rchild);
		
	}
	//2、中序遍历 递归
	public static void midOrderTraversal(TreeNode node) {
		//出口
		if(node==null) return;
		
		//遍历
		midOrderTraversal(node.lchild);
		System.out.print(node.val+" "); // 输出当前节点
		midOrderTraversal(node.rchild);
			
	}
	//3、后序遍历 递归
	public static void postOrderTraversal(TreeNode node) {
		//出口
		if(node==null) return;
		
		//遍历
		postOrderTraversal(node.lchild);
		postOrderTraversal(node.rchild);
		//输出当前节点
		System.out.print(node.val+" ");
		
	}
	//4、层次遍历 队列实现
	public static void levelOrderTraversal(TreeNode root) {
		//队列每次存储每一层的节点
	    ArrayDeque<TreeNode> deque = new ArrayDeque<>();
	    deque.addLast(root); //第一层的节点(根节点)
	    //最终结果
	    LinkedList<Integer> res = new LinkedList<Integer>();
	    
	    //遍历 逐层访问
	    while (!deque.isEmpty()) {
	        int num = deque.size();//队列大小(当前层的节点数量)
	        //保存每一层的所有节点(每一层的结果)
	        //LinkedList<Integer> subList = new LinkedList<Integer>();
	        //当前层
	        for (int i = 0; i < num; i++) {
	        	TreeNode node = deque.removeFirst();//当前层的当前节点
	        	//当前层的当前节点的左右子节点(下一层的节点)
	            if (node.lchild != null) deque.addLast(node.lchild);//下一层的节点
	            if (node.rchild != null) deque.addLast(node.rchild);//下一层的节点
	            //保存当前层的当前节点(保存结果)
	            //subList.add(node.val);
	            res.add(node.val);
	        }
	        //输出(可以获取每一层的结果)
	        //System.out.print(subList);
	    }
	    System.out.print(res);
	}	

	//5、广度优先遍历  队列实现
	public static void breadthFirstSearch(TreeNode node) {
        if(node==null)return;
        
        //队列
        LinkedList<TreeNode> queue = new LinkedList<>();
        queue.add(node);//将根节点存放进队列中
        
        //遍历
        while(!queue.isEmpty()){//只要队列不为空,也就是说没有对树遍历完成
        	//当前节点
        	TreeNode cur = queue.removeFirst();
        	//输出
        	System.out.print(cur.val+" ");
            //获取当前节点的子节点,将子节点存放进队列
            if(cur.lchild!=null)
                queue.add(cur.lchild);
            if(cur.rchild!=null)
                queue.add(cur.rchild);
        }

	}

	//6、深度优先遍历  栈实现
	public static void depthFirstSearch(TreeNode node) {
        if(node==null) return;
        
        //遍历左子节点
        if (node.lchild != null)//先对左节点进行深度遍历
        	depthFirstSearch(node.lchild);
        
        //输出当前节点的值,直到左节点为Null
        System.out.print(node.val+" ");
        
        //遍历右子节点
        if (node.rchild != null)
        	depthFirstSearch(node.rchild);
        
        //最后回溯返回到父节点    
	}
	
	public static void main(String[] args) {	
		//原始节点数据
		LinkedList<Integer> list = new LinkedList<>(Arrays.asList(new Integer[]{1,2,3,null,null,4,5,null,7,null,null,6,null,null}));
		//构建二叉树
		TreeNode root = createBinaryTree(list);
		//遍历二叉树
		System.out.println("1、前序遍历");
		preOrderTraversal(root);
		System.out.println("\n2、中序遍历");
		postOrderTraversal(root);
		System.out.println("\n3、后序遍历");
		midOrderTraversal(root);
		System.out.println("\n4、层次遍历");
		levelOrderTraversal(root);
		System.out.println("\n5、广度优先遍历");
		breadthFirstSearch(root);
		System.out.println("\n6、深度优先遍历");
		depthFirstSearch(root);
	}

}

猜你喜欢

转载自blog.csdn.net/qq_41750911/article/details/127171963