zoukankan      html  css  js  c++  java
  • 二叉树的三种遍历非递归实现(栈) 以及层序遍历(队列)(java)

    先序遍历:根-->左-->右的形式

    public static void preOrderTraveralWithStsck(Node node){
           Stack<Node> stack = new Stack();
    //当节点的左右孩子全为空并且,栈空表示遍历完毕
           while (node != null || !stack.isEmpty()) {
               //访问左孩子并且入栈
               while (node != null) {
                   System.out.print(node.date + " ");
                   stack.push(node);
                   node = node.left;
               }
    //       左孩子遍历完毕,遍历右孩子(栈不为空说明还么有遍历完毕)
               if (!stack.isEmpty()) {
                   node = stack.pop();
                   node = node.right;
               }
           }
        }

    中序遍历:左-->根-->右的形式,与先序遍历很相似,只是打印的位置不同。(相对来说是最简单的)

     public static void inOrderTraveralWithStack(Node node){
           Stack<Node> 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.date+" ");
                   node = node.right;
               }
           }
        }

    后序遍历:左-->右-->根,相比前两种遍历,其应该是最难得,从上面两种遍历可以看出,都是先从根结点出发,依次的找出相对的所有左孩子,然后会出栈到它相对的根结点,再次判断,因此在后序遍历中,访问完左孩子,接下来应该是访问右孩子,所以就应该引入一个变量来记录根结点其右孩子的情况(包括不存在和已经访问过得情况)。

    public static void postOrderTraverTraveralWithStack(Node node){
           Stack<Node> stack = new Stack<>();
           Node pre = null;  //上次访问的节点
           while (node != null || !stack.isEmpty()){
               //将根结点以及所有左孩子入栈
               while (node != null){
                   stack.push(node);
                   node = node.left;
               }
               //走到这说明该节点的左孩子为空了,接下来只需要判断右孩子
               if(!stack.isEmpty()){
                   //获取栈顶元素
                   Node top = stack.peek();
                   //如果栈顶元素的右孩子不存在或者已经被访问了,则输出栈顶元素
                   if(top.right == null || top.right == pre){
                       node = stack.pop();
                       System.out.print(node.date+" ");
                       //为本次访问的节点赋值
                       pre = node;
                       //更新node,很重要否则会进入死循环,(为了访问该节点的根结点)
                       node = null;
                   }//找到栈顶元素的右孩子,并且会将右孩子压入栈(while中),继续迭代
                   else {
                       node = top.right;
                   }
    
               }
    
           }
        }

     层序遍历:按层次关系,横向遍历

    //    层序遍历
        public static void levelOrderTraver(Node node){
            Queue<Node> queue = new LinkedList<>();
    //        插入根结点
            queue.offer(node);
            while (!queue.isEmpty()){
                Node pop = queue.poll();
                System.out.print(pop.date+" ");
                if(pop.left != null){
                    queue.offer(pop.left);
                }
                if(pop.right != null){
                    queue.offer(pop.right);
                }
            }
        }
  • 相关阅读:
    Prometheus环境搭建系列(三):监控redis服务器(redis_exporter)
    Java诊断神器:Arthas常用功能
    sql优化练习
    navicat:[Err] 1055
    Prometheus环境搭建系列(二):监控mysql服务器(mysqld_exporter)
    【笔试必备】常见sql笔试题
    将博客搬至CSDN
    springboot假死、连接泄露
    测试字符串
    阿里云初次使用教程
  • 原文地址:https://www.cnblogs.com/128-cdy/p/13382943.html
Copyright © 2011-2022 走看看