AVL树的插入、删除操作的实现

1.AVL树中插入操作的实现

/**
         * AVL树的插入操作的递归实现
         *
         */
        public void insert(T data){
            this.root = insert(this.root, data);
        }
        /**
         * 以root为根节点,找到合适的插入位置,把子树的根节点返回
         */
        private AVLNode<T> insert(AVLNode<T> root,T data){
            //当根节点为空时,生成一个新节点作为根节点,将data值赋给根节点
            if (this.root==null){
                return new AVLNode<T>(null,null,1);
            }
            if (root.getData().compareTo(data)>0){
                root.setLeft(insert(root.getLeft(),data));
                //此处需要判断root节点是否失衡,以及哪种失衡,并做出相关处理
                if (height(root.getLeft())-height(root.getRight())>1){
                    //左子树过高引起失衡
                    if (height(root.getLeft())-height(root.getRight())>1){
                        //左孩子的左子树过高造成的失衡 对其进行右旋操作
                        root = rotateRight(root);
                    } else {
                        //左孩子的右子树过高 对其进行左平衡
                        root = leftBalance(root);
                    }
                }
            }else if (root.getData().compareTo(data)<0){
                if (height(root.getRight())-height(root.getLeft())>1){
                    //右子树过高引起的失衡
                    if (height(root.getRight())-height(root.getLeft())>1){
                        //右孩子的右子树过高引起的失衡 对其进行左旋操作
                        root = rotateLeft(root);
                    } else {
                        //右孩子的左子树过高引起的失衡 对其进行右平衡
                        root = rightBalance(root);

                    }

                }
            }
            //递归回溯过程中需要更新节点的高度
            root.setHeight(maxHeight(root.getLeft(), root.getRight()) + 1);
            return root;
        }
    

2.AVL树的删除操作的实现

/***
         * AVL树的删除操作的递归实现
         */
        public void remove(T data){
            this.root = remove(this.root,data);
        }
        private AVLNode<T> remove(AVLNode<T> root,T data){
            if (root==null){
                return null;
            }
            if (root.getData().compareTo(data)>0){
                //所要删除的数在左子树
                root.setLeft(remove(root.getLeft(),data));
                //删除data后,AVL树出现失衡
                if (height(root.getRight())-height(root.getLeft())>1){
                    //右子树的两种失衡
                    if (height(root.getRight().getRight())
                            >=height(root.getRight().getLeft())){
                        //当右孩子的右子树过高 对其进行左旋操作
                        root = rotateLeft(root);
                    }else {
                        //当右孩子的左子树过高 对其进行右平衡
                        root = rightBalance(root);
                    }
                }

            }else if (root.getData().compareTo(data)<0){
                //所要删除的数在右子树
                root.setRight(remove(root.getRight(),data));
                if (height(root.getLeft())-height(root.getLeft())>1){
                    //左子树的两种失衡
                    if (height(root.getLeft().getLeft())
                           >=height(root.getLeft().getRight())){
                        //当左孩子的左子树过高 对其进行右旋
                        root = rotateRight(root);
                    }else {
                        //当左孩子的右子树过高,对其进行左平衡
                        root = rightBalance(root);
                    }
                }

            }else {
                if (root.getLeft()!=null&&root.getRight()!=null){
                    // #3 左右子树哪个高,删除哪个,为了防止删除带来的旋转操作,提高效率
                    if (height(root.getLeft())>=height(root.getRight())){
                        //用前驱替换
                        AVLNode<T> pre = root.getLeft();
                        while (pre.getRight()!=null){
                            pre = pre.getRight();
                        }
                        root.setData(pre.getData());
                        root.setLeft(remove(root.getLeft(), pre.getData())); //删除前驱
                    }else {
                        //用后继替换
                        AVLNode<T> post = root.getRight();
                        while (post.getLeft()!=null){
                            post = post.getLeft();
                        }
                        root.setData(post.getData());
                        root.setRight(remove(root.getRight(),post.getData()));//删除后继
                    }
                } else {
                    if (root.getLeft()!= null){
                        return root.getLeft();
                    } else if (root.getRight()!=null){
                        return root.getRight();
                    }else {
                        return null;
                    }
                }
            }
            //在递归回溯过程中,更新节点的高度值
            root.setHeight(maxHeight(root.getLeft(), root.getRight()) + 1);
            return root;
        }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值