zoukankan      html  css  js  c++  java
  • 算法

    二叉树

    二叉树按层遍历打印

    宽度优先遍历,通常使用队列结构。常常有按照层数换行的问题。

    		    1
             /     
            2		3
           /       / 
          4       5   6
                 / 
                7   8    
    output:
    1
    2 3
    4 5 6
    7 8
    

    思路:

    这时可以使用两个变量记录,一个是用变量 last 记录当前的 last 结点,另一个是用变量 nlast 记录下一层的 last 结点。

    pop() 时添加子树,如果 pop 值等于 last 指向的变量,打印换行符号,last 变量指向 nlast。

    nlast 跟踪的是最新加入 queue 的数。

    实现:

    public void printTree(TreeNode root) {
        TreeNode last = null;
        TreeNode nlast = null;
        Queue<TreeNode> queue = new LinkedList<>();
        queue.offer(root);
        last = root;
        nlast = root;
        while (!queue.isEmpty()) {
            TreeNode tmp = queue.poll();
            System.out.print(tmp.val + " ");
            if (tmp.left != null) {
                queue.offer(tmp.left);
                nlast = tmp.left;
            }
            if (tmp.right != null) {
                queue.offer(tmp.right);
                nlast = tmp.right;
            }
            if (tmp == last) {
                last = nlast;
                System.out.println();
            }
        }
    }
    

    测试:

    public static void main(String[] args) {
        // 构建二叉树
        TreeNode root = new TreeNode(1);
        root.left = new TreeNode(2);
        root.right = new TreeNode(3);
        root.left.left = new TreeNode(4);
        root.right.left = new TreeNode(5);
        root.right.right = new TreeNode(6);
        root.right.left.left = new TreeNode(7);
        root.right.left.right = new TreeNode(8);
        PrintBinaryTree test = new PrintBinaryTree();
        test.printTree(root);
    }
    

    二叉树的序列化和反序列化

    方式:先序遍历,中序遍历,后序遍历,层序遍历。

    给定一个二叉树的头节点 head,节点值的类型是 32 位整型。设计序列化和反序列化方案。

    使用树的前序遍历实现序列化:

    public static String serializedBinaryTree(TreeNode root) {
        StringBuilder sb = new StringBuilder();
        preOrderTraversal(root, sb);
        return sb.toString();
    }
    
    private static void preOrderTraversal(TreeNode node, StringBuilder sb) {
        if (node == null) {
            sb.append("#!");
            return;
        }
        sb.append(node.val).append("!");
        preOrderTraversal(node.left, sb);
        preOrderTraversal(node.right, sb);
    }
    

    测试:

    public static void main(String[] args) {
        // 构建二叉树
        TreeNode root = new TreeNode(1);
        root.left = new TreeNode(2);
        root.right = new TreeNode(3);
        root.left.left = new TreeNode(4);
        root.right.left = new TreeNode(5);
        root.right.right = new TreeNode(6);
        root.right.left.left = new TreeNode(7);
        root.right.left.right = new TreeNode(8);
        System.out.println(serializedBinaryTree(root));
    }
    

    输出结果:

    output:
    1!2!4!#!#!#!3!5!7!#!#!8!#!#!6!#!#!
    

    其中 # 表示节点为空,! 是分隔符。

    实现反序列化:

    public static TreeNode deSerializedBinaryTree(String tree) {
        String[] s = tree.split("!");
        Queue<TreeNode> queue = new LinkedList<>();
        for (int i = 0; i < s.length; i++) {
            TreeNode node = null;
            if (s[i].equals("#")) {
                node = new TreeNode(Integer.MIN_VALUE);
            } else {
                node = new TreeNode(Integer.parseInt(s[i]));
            }
            queue.offer(node);
        }
        TreeNode root = queue.poll();
        makeTree(root, queue);
        return root;
    }
    
    private static void makeTree(TreeNode root, Queue<TreeNode> queue) {
        if (root == null || root.val == Integer.MIN_VALUE) {
            return;
        }
        root.left = queue.poll();
        makeTree(root.left, queue);
        root.right = queue.poll();
        makeTree(root.right, queue);
    }
    

    测试,借用了此前实现序列化的树反序列化:

    public static void main(String[] args) {
        // 构建二叉树
        TreeNode root = new TreeNode(1);
        root.left = new TreeNode(2);
        root.right = new TreeNode(3);
        root.left.left = new TreeNode(4);
        root.right.left = new TreeNode(5);
        root.right.right = new TreeNode(6);
        root.right.left.left = new TreeNode(7);
        root.right.left.right = new TreeNode(8);
        System.out.println(serializedBinaryTree(root));
    
        String s = serializedBinaryTree(root);
        TreeNode tree = deSerializedBinaryTree(s);
        printTree(tree);
    }
    

    输出,借用了此前二叉树按层遍历打印的方法,其中空节点用整型的最小值代替:

    		    1
             /     
            2		3
           /       / 
          4       5   6
                 / 
                7   8  
    
    output:
    1 
    2 3 
    4 -2147483648 5 6 
    -2147483648 -2147483648 7 8 -2147483648 -2147483648 
    -2147483648 -2147483648 -2147483648 -2147483648 
    
  • 相关阅读:
    日期获取以及时间转化
    ddt 接口框架数据处理调用excel 处理
    ddt 测试用例UI运用
    动态验证码处理UI自动化获取处理
    Bug Report For .Net (zz.IS2120@BG57IV3)
    中关村翠湖科技园:高端产业聚集区 (zz.IS2120@BG57IV3.T752270541 .K)
    vc6,windows 7 x64 调试 (IS2120@BG57IV3)
    Excel c#Excel文件的操作[转载]
    NUnit学习 标签、方法 记录与说明
    Excel c#Excel工作进程的创建写 与Excel文件的保存[原创] (20100205 11:09)
  • 原文地址:https://www.cnblogs.com/chenxianbin/p/11941631.html
Copyright © 2011-2022 走看看