二叉树的创建,遍历,排序

二叉树

1、什么是二叉树

二叉树是树的一种,每个节点最多可具有两个子树,即结点的度最大为 2(结点度:结点拥

有的子树数)。
在这里插入图片描述

2、二叉树种类

二叉查找树(binary search tree):

当前根节点的左边全部比根节点小,当前根节点的右边全部比根节点大。

斜树:

所有结点都只有左子树,或者右子树。

在这里插入图片描述

满二叉树

所有的分支节点都具有左右节点。

在这里插入图片描述

完全二叉树

若设二叉树的深度为 h,除第 h 层外,其它各层 (1~h-1) 的结点数都达到最大个数,第 h

层所有的结点都连续集中在最左边,这就是完全二叉树。

在这里插入图片描述

3、二叉树的一些性质

二叉树第 i 层上的结点数目最多为 2^(i-1) (i≥1)

深度为 h 的二叉树至多有 2^h-1 个结点(h≥1)

包含 n 个结点的二叉树的高度至少为 log2 (n+1)

在任意一棵二叉树中,若终端结点的个数为 n0,度为 2 的结点数为 n2,则 n0=n2+1

4、二叉树的遍历

先序遍历

先访问根节点,再访问左节点,再访问右节点

中序遍历

先访问左节点,再访问根节点,再访问右节点

后序遍历

先访问左节点,再访问右节点,再访问根节点

提示:遍历方式是根据根节点的位置不同,而起名的。左右节点访问顺序不会改变

在这里插入图片描述

先序遍历(根-左-右):1-2-4-8-9-5-10-3-6-7

中序遍历:(左-根-右):8-4-9-2-10-5-1-6-3-7

后序遍历(左-右-根):8-9-4-10-5-2-6-7-3-1

5、代码实现

树的结构
public class TreeNode<T> {
    private T data;
    private TreeNode left;
    private TreeNode right;

    public TreeNode(T data) {
        this.data = data;
    }

    public T getData() {
        return data;
    }

    public void setData(T data) {
        this.data = data;
    }

    public TreeNode getLeft() {
        return left;
    }

    public void setLeft(TreeNode left) {
        this.left = left;
    }

    public TreeNode getRight() {
        return right;
    }

    public void setRight(TreeNode right) {
        this.right = right;
    }
}
手动构建二叉树+遍历
public class TestMain {
    public static void main(String[] args) {
        TreeNode<String> root = new TreeNode<>("1");
        TreeNode<String> node2 = new TreeNode<>("2");
        TreeNode<String> node3 = new TreeNode<>("3");
        TreeNode<String> node4 = new TreeNode<>("4");
        TreeNode<String> node5 = new TreeNode<>("5");
        TreeNode<String> node6 = new TreeNode<>("6");
        TreeNode<String> node7 = new TreeNode<>("7");


        // 手动构建二叉树
        root.setLeft(node2);
        node2.setLeft(node4);
        node2.setRight(node5);
        root.setRight(node3);
        node3.setLeft(node6);
        node3.setRight(node7);
        System.out.println("广度遍历:");
        printByLayer(root);
        System.out.println("\n前序遍历:");
        pre_print(root);
        System.out.println("\n中序遍历:");
        mid_print(root);
        System.out.println("\n后序遍历:");
        last_print(root);
    }

    /**
     * 按广度遍历
     * @param root
     */
    public static void printByLayer(TreeNode root){
        if (root == null) return;
        Queue<TreeNode> queue = new LinkedList<>();
        queue.add(root);
        // 当队列不为空
        while(!queue.isEmpty()){
            TreeNode temp = queue.poll();
            if (temp.getLeft()!=null){
                // 进队列
                queue.add(temp.getLeft());
            } if (temp.getRight() != null){
                // 进队列
                queue.add(temp.getRight());
            }
            System.out.print(temp.getData()+"\t");
        }
    }

    /**
     * 前序遍历:根左右
     * @param root
     */
    public static void pre_print(TreeNode root) {
        if (root != null) {
            // 根
            System.out.print(root.getData()+"\t");
            // 左
            pre_print(root.getLeft());
            // 右
            pre_print(root.getRight());
        }
    }

    /**
     * 中序遍历: 左根右
     * @param root
     */
    public static void mid_print(TreeNode root) {
        if (root != null) {
            // 左
            mid_print(root.getLeft());
            // 根
            System.out.print(root.getData()+"\t");
            // 右
            mid_print(root.getRight());
        }
    }

    /**
     * 后序遍历: 左右根
     * @param root
     */
    public static void last_print(TreeNode root) {
        if (root != null) {
            // 左
            last_print(root.getLeft());
            // 右
            last_print(root.getRight());
            // 根
            System.out.print(root.getData()+"\t");
        }
    }

}

运行结果

广度遍历:
1	2	3	4	5	6	7	
前序遍历:
1	2	4	5	3	6	7	
中序遍历:
4	2	5	1	6	3	7	
后序遍历:
4	5	2	6	7	3	1
排序二叉树
/**
 * 二叉排序树
 */
public class BinarySortTree<T> {
    private TreeNode<T> root; // 根节点

    public TreeNode<T> getRoot() {
        return root;
    }

    public void setRoot(TreeNode<T> root) {
        this.root = root;
    }

    /**
     * 获取节点
     * @param data
     * @return
     */
    public  TreeNode get(T data){
        if (this.root == null) return null;
        TreeNode temp = root;
        while (temp != null){
            String currentData = String.valueOf(temp.getData());
            String nodeData = String.valueOf(data);
            if (currentData.compareTo(nodeData) > 0){
                //根节点大 往左边走
                temp = temp.getLeft();
            } else if (currentData.compareTo(nodeData) < 0){
                //根节点小 往右边走
                temp = temp.getRight();
            } else {
                return temp;
            }
        }
        return null;
    }

    /**
     * 根据结点节点大小插入
     * @param data treeNode节点
     * @return
     */
    public boolean add(TreeNode<T> data) {
        if (root == null) {
            this.root = data;
            return true;
        } else {
            TreeNode<T> current = root;
            TreeNode<T> parentNode = null;
            while(current != null) {
                parentNode = current;
                String currentData = (String)parentNode.getData();
                String nodeData = (String)data.getData();

                //转换成字符串比较
                if (currentData.compareTo(nodeData) > 0) {
                    // 根节点大
                    if (parentNode.getLeft() == null){
                        // 插入左子树
                        parentNode.setLeft(data);
                        return true;
                    }
                    // 继续看左子树
                    current = parentNode.getLeft();
                } else {
                    // 根节点小
                    if (parentNode.getRight() == null){
                        // 插入右子树
                        parentNode.setRight(data);
                        return true;
                    }
                    // 继续看右子树
                    current = parentNode.getRight();
                }
            }
        }
        return false;
    }
}

test

public class TestMain {
    public static void main(String[] args) {
        TreeNode<String> root = new TreeNode<>("a14");
        TreeNode<String> node2 = new TreeNode<>("b25");
        TreeNode<String> node3 = new TreeNode<>("c10");
        TreeNode<String> node4 = new TreeNode<>("d18");
        TreeNode<String> node5 = new TreeNode<>("d13");
        //排序二叉树
        BinarySortTree<String> btree = new BinarySortTree<String>();
        btree.add(root);
        btree.add(node2);
        btree.add(node3);
        btree.add(node4);
        btree.add(node5);
        System.out.println("\n中序遍历:");
        mid_print(btree.getRoot());
        TreeNode d13 = btree.get("d13");
        System.out.println("\n" + d13.getData());
    }

    /**
     * 中序遍历: 左根右
     * @param root
     */
    public static void mid_print(TreeNode root) {
        if (root != null) {
            // 左
            mid_print(root.getLeft());
            // 根
            System.out.print(root.getData()+"\t");
            // 右
            mid_print(root.getRight());
        }
    }


}

运行结果

中序遍历:
a14	b25	c10	d13	d18	
d13

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值