平衡二叉树

平衡二叉树又称AVL树。它或者是一棵空树,或者是具有下列性质的二叉树:
它的左子树和右子树都是平衡二叉树,且左子树和右子树的深度之差的绝对值不超过1。
若将二叉树上节点的平衡因子定位为该节点的左子树的深度减去它的右子树的深度,则平衡二叉树上所有节点的平衡因子只可能是-1、0、1。
只要二叉树上有一个节点的平衡因子的绝对值大于1,则该二叉树就是不平衡的。
在这里插入图片描述

public class AVL {

    private boolean taller=false;
    private Node root =null;
    private static final int EH=0;
    private static final int LH=1;
    private static final int RH=-1;

    private class Node{
        public int data;
        public Node leftChild;
        public Node rightChild;
        public int balanceFactor;

        public Node(int data){
            this.data=data;
            balanceFactor=0;
        }
    }

    public  Node RRotate(Node T){
        Node temp=T.leftChild;
        T.leftChild=temp.rightChild;
        temp.rightChild=T;
        return temp;
    }

    public  Node LRotate(Node T){
        Node temp=T.rightChild;
        T.rightChild=temp.leftChild;
        temp.leftChild=T;
        return  temp;
    }

    public  Node leftBalance(Node node,Node preNode){
        Node child=node.leftChild;
        Node root=null;
        switch (child.balanceFactor){
            case LH:
                node.balanceFactor=child.balanceFactor=EH;
                root=RRotate(node);
                if(preNode!=null && node.data< preNode.data){
                    preNode.leftChild=root;
                }
                if(preNode!=null && node.data> preNode.data){
                    preNode.rightChild=root;
                }
                break;
            case RH:
                Node rchild=child.rightChild;
                switch (rchild.balanceFactor){
                    case EH:
                        node.balanceFactor=child.balanceFactor=EH;
                        break;
                    case LH:
                        node.balanceFactor=RH;
                        child.balanceFactor=EH;
                        break;
                    case RH:
                        node.balanceFactor=EH;
                        child.balanceFactor=LH;
                        break;
                    default:break;
                }
                rchild.balanceFactor=EH;
                node.leftChild=LRotate(child);
                root=RRotate(node);
                if(preNode!=null && node.data<preNode.data){
                    preNode.leftChild=root;
                }
                if(preNode!=null && node.data>preNode.data){
                    preNode.rightChild=root;
                }
                break;
            default:break;
        }
        return root;
    }

    public  Node rightBalance(Node node,Node preNode){
        Node child=node.rightChild;
        Node root=null;
        switch (child.balanceFactor){
            case RH:
                node.balanceFactor=child.balanceFactor=EH;
                root=LRotate(node);
                if(preNode!=null && node.data<preNode.data){
                    preNode.leftChild=root;
                }
                if(preNode!=null && node.data>preNode.data){
                    preNode.rightChild=root;
                }
                break;
            case LH:
                Node lchild=child.leftChild;
                switch (lchild.balanceFactor){
                    case EH:
                        node.balanceFactor=child.balanceFactor=EH;
                        break;
                    case RH:
                        node.balanceFactor=LH;
                        child.balanceFactor=EH;
                        break;
                    case LH:
                        node.balanceFactor=EH;
                        child.balanceFactor=RH;
                        break;
                    default:break;
                }
                lchild.balanceFactor=EH;
                node.rightChild=RRotate(child);
                root=LRotate(node);
                if(preNode!=null && node.data<preNode.data){
                    preNode.leftChild=root;
                }
                if( preNode!=null && node.data>preNode.data){
                    preNode.rightChild=root;
                }
                break;
            default:break;
        }
        return root;
    }

    public boolean insertNode(int value){
       return insertNode(root,value,null);
    }

    public  boolean insertNode(Node node, int value, Node preNode){
        if(node==null){
            node=new Node(value);
            node.balanceFactor=EH;
            taller=true;
            if(preNode!=null && node.data< preNode.data){
                preNode.leftChild=node;
            }
            if(preNode!=null && node.data> preNode.data){
                preNode.rightChild=node;
            }
            root =node;
            return true;
        }else{
            if(value==node.data){
                root =node;
                return false;
            }
            if (value<node.data){
                if (!insertNode(node.leftChild, value, node)) {
                    root =node;
                    return false;
                }
                if(taller){
                    switch (node.balanceFactor){
                        case EH:taller=true;node.balanceFactor=LH;break;
                        case RH:taller=false;node.balanceFactor=EH;break;
                        case LH:
                            taller=false;
                            node=leftBalance(node,preNode);
                            if(preNode!=null){
                                node=preNode;
                            }
                            break;
                        default:break;
                    }
                }
            }
            if (value>node.data){
                if (!insertNode(node.rightChild, value,node)) {
                    root =node;
                    return false;
                }
                if(taller){
                    switch (node.balanceFactor){
                        case EH:taller=true;node.balanceFactor=RH;break;
                        case LH:taller=false;node.balanceFactor=EH;break;
                        case RH:
                            taller=false;
                            node=rightBalance(node,preNode);
                            if(preNode!=null){
                                node=preNode;
                            }
                            break;
                        default:break;
                    }
                }
            }
        }
        root =node;
        return true;
    }

    public void inorderTraversal(){
        inorderTraversal(root);
    }

    public  void inorderTraversal(Node root){
        if(root!=null){
            inorderTraversal(root.leftChild);
            System.out.println("节点:"+root.data+"  平衡因子:"+root.balanceFactor);
            inorderTraversal(root.rightChild);
        }
        return ;
    }

    public static void main(String[] args) {
        //int[] data={8,6,4};
        //int[] data={8,6,9,5,7,3};
        //int[] data={8,6,7};
        //int[] data={8,5,9,4,6,7};
        //int[] data={8,5,9,4,7,6};
        int[] data={8,5,9,7,6};
        AVL avl=new AVL();
        for(int i=0;i<data.length;i++){
            avl.insertNode(data[i]);
        }
        avl.inorderTraversal();
    }
}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值