• 数据结构之二叉树的遍历


    二叉树的遍历是指按照某条搜索路径访问树中的每个节点,使得每个节点的均只被访问一次。由二叉树的递归定义,遍历一棵二叉树便要决定对根节点、左子树和右子树的访问顺序。常见的遍历次序有先序遍历、中序遍历和后序遍历。其中序指的是根节点在何时被访问。

    1. 先序遍历(PreOrder):若二叉树非空,则先访问根节点,再访问左子树,最后访问右子树。

    2. 中序遍历(InOrder):若二叉树非空,则先访问左子树,再访问根节点,最后访问右子树。

    3. 后序遍历(PostOder):若二叉树非空,则先访问左子树,再访问右子树,最后访问根节点。

    节点结构如下:

     1 /**
     2  * 二叉树节点结构
     3  * Created by Administrator on 2017/5/2 0002.
     4  */
     5 public class TreeNode {
     6     public int val;
     7     public TreeNode left;
     8     public TreeNode right;
     9     public TreeNode(int x){
    10         this.val = x;
    11     }
    12 }

    自定义节点处理函数:

    1 /*对每个节点进行处理*/
    2 public static void process(int v){
    3     System.out.println(v);
    4 }

    先序遍历

    1 /*递归形式*/
    2 public static void preOrder(TreeNode root){
    3         if(root == null){
    4             return;
    5         }
    6         process(root.val);
    7         preOrder(root.left);
    8         preOrder(root.right);
    9     }
     1 //非递归形式,借助栈
     2     public static void preOrder2(TreeNode root) {
     3 
     4         if (root == null) {
     5             return;
     6         }
     7 
     8         Stack<TreeNode> stack = new Stack<>();
     9 
    10         while (root != null || !stack.isEmpty()) {
    11             while (root != null) {
    12                 print(root.val);
    13                 stack.push(root);
    14                 root = root.left;
    15             }
    16 
    17             if (!stack.isEmpty()) {
    18                 root = stack.peek();
    19                 stack.pop();
    20                 root = root.right;
    21             }
    22         }
    23     }

    中序遍历

     1 /*递归形式*/
     2 public static void inOrder(TreeNode root){
     3     if(root == null){
     4         return;
     5     }
     6     if(root.left != null){
     7         inOrder(root.left);
     8     }
     9     process(root.val);
    10     if(root.right != null){
    11         inOrder(root.right);
    12     }    
    13 }
     1 /*非递归形式*/
     2 public static void inOrder(TreeNode root){
     3     if(root == null){
     4         return;
     5     }
     6     Stack<TreeNode> st = new Stack<TreeNode>();
     7     st.push(root);
     8     TreeNode tmp;
     9     while (!st.empty()){
    10         tmp = st.peek();
    11         while (tmp != null){
    12             st.push(tmp.left);
    13             tmp = tmp.left;
    14         }
    15         if(tmp == null){
    16             st.pop();
    17         }
    18         if(!st.empty()) {
    19             tmp = st.pop();
    20             process(tmp.val);
    21             st.push(tmp.right);
    22         }
    23     }
    24 }

    后序遍历

     1 /*递归形式*/
     2 public static void postOrder(TreeNode root){
     3     if(root == null){
     4         return;
     5     }
     6     if(root.left != null){
     7         postOrder(root.left);
     8     }
     9     if(root.right != null){
    10         postOrder(root.right);
    11     }
    12     process(root.val);
    13 }
     1 /*后序非递归形式*/
     2 public static void postOrder(TreeNode root){
     3    if (root == null) {
     4             return;
     5         }
     6 
     7         Stack<TreeNode> stack = new Stack<>();
     8         TreeNode node = root;
     9         //最后访问的节点
    10         TreeNode lastVisit = root;
    11         while (node != null || !stack.isEmpty()) {
    12 
    13             //左子树入栈
    14             while (node != null) {
    15                 stack.push(node);
    16                 node = node.left;
    17             }
    18 
    19             //查看当前栈顶元素
    20             node = stack.peek();
    21 
    22             //如果其右子树也为空,或者右子树已经访问
    23             //则可以直接输出当前节点的值
    24             if (node.right == null || node.right == lastVisit) {
    25                 print(node.val);
    26                 stack.pop();
    27                 lastVisit = node;
    28                 node = null;
    29             } else {
    30                 //否则遍历右子树
    31                 node = node.right;
    32             }
    33         }
    34 }
  • 相关阅读:
    PHP 生成随机字符串与唯一字符串
    大数据和AI怎么与现代教育相结合?
    大数据和AI怎么与现代教育相结合?
    python正常时间和unix时间戳相互转换的方法
    python正常时间和unix时间戳相互转换的方法
    人人都谈大数据,你考虑过小数据的感受吗
    人人都谈大数据,你考虑过小数据的感受吗
    浅析机器学习的主题模型和语义分析
    浅析机器学习的主题模型和语义分析
    大数据对当代企业推广价值何在
  • 原文地址:https://www.cnblogs.com/lfeng1205/p/6804110.html
Copyright © 2020-2023  润新知