AVL树 java代码 插入方法

代码如下

public class AVLTree<T extends Comparable<? super T>> {

    private AVLNode<T> root;

    /**
     * 插入
     * @param t 待插入的元素 不可为空
     */
    public void insert(T t) {
        root = insert_0(root,t);
    }

    private AVLNode<T> insert_0(AVLNode<T> currRoot , T value){
        if(currRoot==null)return new AVLNode<>(value,null,null);

        if(value.compareTo(currRoot.value)<0){
            currRoot.left = insert_0(currRoot.left,value);
        }else if(value.compareTo(currRoot.value)>0){
            currRoot.right = insert_0(currRoot.right,value);
        }
        //更新高度
        currRoot.height = Math.max(height(currRoot.left),height(currRoot.right)) + 1;
        //平衡本节点子树
        currRoot = balance(currRoot);
        return currRoot;
    }

    /**
     * 平衡一个节点子树
     * @param currRoot
     * @return
     */
    private AVLNode<T> balance(AVLNode<T> currRoot ){
        if(isUnbalance(currRoot))return currRoot;
        else {
            if(height(currRoot.left)>height(currRoot.right)){
                if(height(currRoot.left.left)>=height(currRoot.left.right)){//左左,这里用大于等于,是为了在删除后的平衡操作中,兼容 两个一样高的子树,插入不会导致两个一样超高的子树,但删除却会
                    currRoot = rotateLeftLeft(currRoot);
                }
                if(height(currRoot.left.right)>height(currRoot.left.left)) {//左右
                    currRoot = rotateLeftRight(currRoot);
                }
            }else{
                if(height(currRoot.right.right)>=height(currRoot.right.left)){//右右
                    currRoot = rotateRightRight(currRoot);
                }
                if(height(currRoot.right.left)>height(currRoot.right.right)) {//右左
                    currRoot = rotateRightLeft(currRoot);
                }
            }
        }
        //发生平衡后,更新高度
        refreshHeight(currRoot);
        return currRoot;
    }

    /**
     * 左左单选转
     * @param currRoot
     * @return
     */
    private AVLNode<T> rotateLeftLeft(AVLNode<T> currRoot){
        AVLNode<T> left = currRoot.left;
        AVLNode<T> leftRight = left.right;
        left.right = currRoot;
        currRoot.left=leftRight;
        return left;
    }

    /**
     * 左右双旋转(可通过先对左节点进行右旋转,再对本节点进行左旋转完成。但本处没有这么做)
     * @param currRoot
     * @return
     */
    private AVLNode<T> rotateLeftRight(AVLNode<T> currRoot){
        AVLNode<T> left = currRoot.left;
        AVLNode<T> leftLeft = left.left;
        AVLNode<T> leftRight = left.right;
        AVLNode<T> leftRightLeft = leftRight.left;
        AVLNode<T> leftRightRight = leftRight.right;

        left.right = leftRightLeft;

        currRoot.left = leftRightRight;

        leftRight.left = left;

        leftRight.right = currRoot;

        return leftRight;

    }

    /**
     * 右右单旋转
     * @param currRoot
     * @return
     */
    private AVLNode<T> rotateRightRight(AVLNode<T> currRoot){
        AVLNode<T> right = currRoot.right;
        AVLNode<T> rightLeft = right.left;
        right.left = currRoot;
        currRoot.right=rightLeft;
        return right;
    }

    /**
     * 右左双旋转
     * @param currRoot
     * @return
     */
    private AVLNode<T> rotateRightLeft(AVLNode<T> currRoot){
        AVLNode<T> right = currRoot.right;
        AVLNode<T> rightRight = right.right;
        AVLNode<T> rightLeft = right.left;
        AVLNode<T> rightLeftRight = rightLeft.right;
        AVLNode<T> rightLeftLeft = rightLeft.left;

        right.left = rightLeftRight;

        currRoot.right = rightLeftLeft;

        rightLeft.right = right;

        rightLeft.left = currRoot;

        return rightLeft;

    }

    /**
     * 节点是否不平衡
     * @param currRoot
     * @return
     */
    private boolean isUnbalance(AVLNode<T> currRoot) {
        return Math.abs(height(currRoot.left) - height(currRoot.right))<=1;
    }

    /**
     * 计算高度
     * @param node
     * @return
     */
    private int height(AVLNode<?> node){
        return AVLNode.height(node);
    }

    /**
     * 更新高度
     * @param node
     * @return
     */
    private int refreshHeight(AVLNode<?> node){
        if(node==null)return -1;
        int leftH = refreshHeight(node.left);
        int rightH = refreshHeight(node.right);
        node.height = Math.max(leftH,rightH)+1;
        return node.height;
    }

    private static class AVLNode<E extends Comparable<? super E>>{
        E value;
        AVLNode<E> left;
        AVLNode<E> right;
        int height;
        AVLNode(E value , AVLNode<E> left , AVLNode<E> right){
            this.value = value;
            this.left = left;
            this.right = right;
            height = 0;
        }
        static int height(AVLNode<?> node){
            return node==null?-1:node.height;
        }
    }

}

 

posted @ 2022-08-18 16:08  向金华  阅读(46)  评论(0)    收藏  举报