数据结构(四) 二分搜索树1

 

一 为什么要研究树结构

二 二叉树

三 二分搜索树

public class BST<E extends Comparable<E>> {

    private class Node{
        public E e;
        public Node left, right;

        public Node(E e){
            this.e =e;
            left = null;
            right = null;
        }
    }

    private Node root;
    private int size;

    public BST(){
        root = null;
        size = 0;
    }

    public int size(){
        return size;
    }

    public boolean isEmpty(){
        return size == 0;
    }

    public void add(E e){
        if(root == null){
            root = new Node(e);
            size++;
        }else
            add(root, e);
    }
    //向以node为根的二分搜索树中插入元素e 递归算法
    private void add(Node node, E e){
        if(e.equals(node.e))
            return;
        else if(e.compareTo(node.e) < 0 && node.left == null ){   //因为不是基础类型必须用compateTo 来比较
            node.left = new Node(e);
            size++;
            return;
        }
        else if(e.compareTo(node.e) > 0 && node.right == null ){   //因为不是基础类型必须用compateTo 来比较
            node.right = new Node(e);
            size++;
            return;
        }
        //以上是递归结束条件

        if(e.compareTo(node.e) < 0){
            add(node.left, e);
        }
        else //>>0的情况
            add(node.right,e);
    }

}

第二种改进add方法

public class BST<E extends Comparable<E>> {

    private class Node{
        public E e;
        public Node left, right;

        public Node(E e){
            this.e =e;
            left = null;
            right = null;
        }
    }

    private Node root;
    private int size;

    public BST(){
        root = null;
        size = 0;
    }

    public int size(){
        return size;
    }

    public boolean isEmpty(){
        return size == 0;
    }

    public void add(E e){
            add(root, e);
    }
    //向以node为根的二分搜索树中插入元素e 递归算法
    private Node add(Node node, E e){  //新的递归解法: 把空看作也是一颗二叉树 如果递归是空的话 就给创建新节点给该节点复制
       if(node == null){
           size++;
           return new Node(e);
        }
        //以上是递归结束条件

        if(e.compareTo(node.e) < 0){
            node.left = add(node.left, e);
        }
        else if (e.compareTo(node.e) > 0))//>>0的情况
            node.right = add(node.right,e);
        return node;
    }

}

查询方法

 //看以node为根的二分搜索树中是否包含元素e,递归算法
    private boolean contains(Node node , E e){
        if(node == null)
            return false;
        if(e.compareTo(node.e) ==0)
            return true;
        else if(e.compareTo(node.e) < 0)
            return  contains(node.left, e);
        else
            return contains(node.right, e);
    }
}

前序遍历

 //二分搜索树前序遍历
    public void preOrder(){
        preOrder(root);
    }
    private void preOrder(Node node){
        if(node == null)
            return;
        System.out.println(node.e);
        preOrder(node.left);
        preOrder(node.right);
    }
    @Override
    public String toString(){
        StringBuilder res = new StringBuilder();
        generateBSTString(root, 0, res);
        return res.toString();
    }

    //生成以node为根节点,深度为de'pth的深度二叉树字符串
    private void generateBSTString(Node node, int depth, StringBuilder res){
        if(node == null){
            res.append(generateDepthString(depth) + "null\n");
            return;
        }
        res.append(generateDepthString(depth)+ node.e+ "\n");
        generateBSTString(node.left, depth +1, res);
        generateBSTString(node.right, depth +1, res);
    }

    private String generateDepthString(int depth){
        StringBuilder res = new StringBuilder();
        for(int i=0; i< depth; i++){
            res.append("--");
        }
        return res.toString();
    }

中序遍历后序遍历

//中序遍历
    public void inOrder(){
        inOrder(root);
    }

    private void inOrder(Node node){
        if(node == null){
            return;
        }
        inOrder(node.left);
        System.out.println(node.e);
        inOrder(node.right);
    }
//后序遍历
    public void postOrder(){
        inOrder(root);
    }
    private void postOrder(Node node){
        if(node == null)
            return;
        postOrder(node.left);
        postOrder(node.right);
        System.out.println(node.e);
    }

前中后遍历每结束一个左右子树都回到根节点

前序遍历的非递归实现

//非递归实现前序遍历
    public void preOrderNR(){
        Stack<Node> stack =  new Stack<>();
        stack.push(root);
        while(!stack.isEmpty()){
            Node cur = stack.pop();
            System.out.println(cur.e);

            if(cur.right != null){
                stack.push(cur.right);
            }
            if(cur.left != null){
                stack.push(cur.left);
            }
        }
    }

层序遍历实现

/层序遍历
    public void levelOrder(){
        Queue<Node> q = new LinkedList<>();
        q.add(root);
        while(!q.isEmpty()){
            Node cur = q.remove();
            System.out.println(cur.e);

            if(cur.left != null)
                q.add(cur.left);
            if(cur.right != null)
                q.add(cur.right);
        }

    }

深度优先遍历“从上往下按深度找

广度优先遍历:从左往右按层查找

删除二分搜索树中的元素

1)最大值和最小值

//寻找二分搜索树的最小元素
    public E minimum(){
        if(size == 0){
            throw new IllegalArgumentException("BST is empty");
        }
        return minimum(root).e;
    }
    //返回以root为根的二分搜索树最小的节点
    private Node minimum(Node node){
        if(node.left == null)
            return  node;
        return minimum(node.left); //此时相当于在操作一个链表 只向左走;
    }

    //寻找二分搜索树的最小元素
    public E maxmum(){
        if(size == 0){
            throw new IllegalArgumentException("BST is empty");
        }
        return maxmum(root).e;
    }
    //返回以root为根的二分搜索树最小的节点
    private Node maxmum(Node node){
        if(node.right == null)
            return  node;
        return maxmum(node.right); //此时相当于在操作一个链表 只向左走;
    }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值