平衡二叉树

1概念

    平衡二叉树(Balanced Binary TreeHeight-Balanced Tree)又称AVL树(根据它的发明者G.M.Adelson-VelskyE.M.Landis命名的)。它或者是一棵空树,或者是具有下列性质的二叉树:它的左子树和右子树都是平衡二叉树,且左子树和右子树的深度之差的绝对值不超过1.

    若将二叉树上结点的平衡因子BFBalance Factor)定义为该结点的左子树的深度减去它的右子树的深度,则平衡二叉树上所有结点的平衡因子只可能是-1,01.

    只要二叉树上有一个结点的平衡因子的绝对值大于1,则该二叉树就是不平衡的。

2旋转

    由一个正序序列{1,2,3,4,5,6,7,8}构成一个二叉搜索树时,如图2所示,它将退化为链表,使得查找时出现最坏的情况——时间复杂度为O(n)。故而希望使由无序序列构成的二叉搜索树成为平衡二叉树。因为AVL树上任何结点的左右子树的深度之差都不超过1,即它的深度和logn是同数量级的,因此它的平均查找长度也和logn同数量级。

一般来说,在AVL树中进行插入或删除结点后,可能导致AVL树失去平衡。失去平衡的AVL树可以概括为4种类型:LL型、LR型、RR型和RL型。

(1)LL型(Left-Left型),在左子树的左边结点进行插入


在左子树的左边结点插入结点1之后,使得结点3失去平衡,这种就是失衡的LL型,可通过单向右旋平衡处理:让s变成根结点,s的右子树变成p的左子树,p变成s的右子树

/*二叉搜索树结点*/
typedef struct bst_node
{
    int data;
    int bf;/*结点的平衡因子*/
    struct bst_node *lchild;
    struct bst_node *rchild;
}bst_node_t, bst_tree_t;


/*右旋平衡处理: 对以p为根的二叉搜索树作右旋处理,处理后p指向新的树根结点*/
void r_rotate(bst_tree_t **p)
{
    bst_tree_t *s;
    s = (*p)->lchild;         /*s为p的左子树根结点*/
    (*p)->lchild = s->rchild; /*s的右子树作为p的左子树*/
    s->rchild = *p;           /*p作为s的右子树*/
    *p = s;                   /*s作为根结点,p指向新的根结点*/
}

(2)RR型(Right-Right型),在右子树的右边结点插入


在右子树的右边结点插入结点5之后,使得结点3失去平衡,这种就是失衡的RR型,可通过单向左旋平衡处理:让s变成根结点,s的左子树变成p的右子树,p变成s的左子树。

/*左旋平衡处理:对以p为根结点的二叉搜索树作左旋处理,处理后,p指向新的根结点*/
void l_rotate(bst_tree_t **p)
{
    bst_tree_t *s;
    s = (*p)->rchild;        /*s为p的右子树根结点*/
    (*p)->rchild = s->lchild;/*s的左子树作为p的右子树*/
    s->lchild = *p;          /*p作为s的左子树*/
    *p = s;                  /*s作为根结点,p指向新的根结点*/
}

(3)LR型(Left-Right型),在左子树的右边结点插入


在左子树的右边结点插入结点3之后,使得结点5失去平衡,这种就是失衡的LR型。对这种情况,先作左旋处理,再作右旋处理。

(4)RL型(Right-Left型),在右子树的左边结点插入


在右子树的左边结点插入结点18之后,使得结点15失去平衡,这种就是失衡的RL型。对这种情况,现在右旋处理,再作左旋处理。



评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值