平衡二叉树或是一棵空树,或是具有下列性质的二叉排序树:其左子树和右子树都是平衡二叉树,而且左右子树深度之差绝对值不超过1. 由此引出了平衡因子(balance factor)的概念,bf定义为该结点的左子树的深度减去右子树的深度(有些书是右子树深度减去左子树深度,我是按照左子树减去右子树来计算的,下面的代码也是这样定义的),所以平衡二叉树的结点的平衡因子只可能是 -1,0,1 ,某个结点的平衡因子绝对值大于1,该二叉树就不平衡。
平衡二叉树在出现不平衡状态的时候,要进行平衡旋转处理,有四种平衡旋转处理(单向右旋处理,单向左旋处理,双向旋转(先左后右)处理,双向旋转(先右后左)处理),归根到底是两种(单向左旋处理和单向右旋处理)。
下面是四种旋转的示意图:
图1 LL旋转 和 RR旋转
图2 LR旋转
图3 LR旋转和LL旋转
图4 RL旋转
图5 LR旋转
这四种旋转可以归纳为两类:LL旋转和LR旋转可以归为左旋转,RR旋转和RL旋转归为右旋转。
类型定义:
typedef struct AVLNode * AVLTree;
typedef struct AVLNode{
int data;
short int bf;
AVLTree lchild,rchild;
}AVLNode;
左旋函数:
void leftRotate(AVLTree *root,bool *unbalanced)
{
AVLTree child,gchild;//gchild : grand child
child = (*root)->lchild;
if (child->bf == 1) {
/* LL rotation */
(*root)->lchild = child->rchild;
child->rchild = *root;
(*root)->bf = 0;
(*root) = child;
}
else {
/* LR rotation */
gchild = child->rchild;
child->rchild = gchild->lchild;
gchild->lchild = child;
(*root)->lchild = gchild->rchild;
gchild->rchild = *root;
switch (gchild->bf) {
case 1: (*root)->bf = -1;
child->bf = 0;
break;
case 0: (*root)->bf = child->bf = 0;
break;
case -1: (*root)->bf = 0;
child->bf = 1;
}
*root = gchild;
}
(*root)->bf = 0;
*unbalanced = false;
}
右旋函数:
void rightRotate(AVLTree *root, bool *unbalanced)
{
AVLTree child,gchild;/*gchild : grand child*/
child = (*root)->rchild;
if (child->bf == -1) {
/* RR rotation */
(*root)->rchild = child->lchild;
child->lchild = *root;
(*root)->bf = 0;
(*root) = child;
}
else {
/* RL rotation */
gchild = child->lchild;
child->lchild = gchild->rchild;
gchild->rchild = child;
(*root)->rchild = gchild->lchild;
gchild->lchild = *root;
switch (gchild->bf) {
case -1: (*root)->bf = 1;
child->bf = 0;
break;
case 0: (*root)->bf = child->bf = 0;
break;
case 1: (*root)->bf = 0;
child->bf = -1;
}
*root = gchild;
}
(*root)->bf = 0;
*unbalanced = false;
}
AVL树的插入函数:
void AVLInsert(AVLTree *root, int x, bool *unbalanced)
{
if(*root == NULL){
/* insert into a null tree */
*unbalanced = true;
*root = new AVLNode;
(*root)->lchild = (*root)->rchild = NULL;
(*root)->bf = 0;
(*root)->data = x;
}
else if (x < (*root)->data) {
AVLInsert(&((*root)->lchild),x,unbalanced);
if (*unbalanced)
/* left branch has grown higher */
switch ((*root)->bf) {
case -1: (*root)->bf = 0;
*unbalanced = false;
break;
case 0: (*root)->bf = 1;
break;
case 1: leftRotate(root,unbalanced);
}
}
else if (x > (*root)->data) {
AVLInsert(&((*root)->rchild), x, unbalanced);
if (*unbalanced)
/* right branch has grown higher */
switch ((*root)->bf){
case 1: (*root)->bf = 0;
*unbalanced = false;
break;
case 0: (*root)->bf = -1;
break;
case -1: rightRotate(root,unbalanced);
}
}
else {
*unbalanced = false;
cout<<"Node x = "<<x<<" is alreay in the tree."<<endl;
}
}
从0到9到插入结果
0
---------------------cut---------------------
0
\
1
---------------------cut---------------------
1
/ \
0 2
---------------------cut---------------------
1
/ \
0 2
\
3
---------------------cut---------------------
1
/ \
0 3
/ \
2 4
---------------------cut---------------------
3
/ \
1 4
/ \ \
0 2 5
---------------------cut---------------------
3
/ \
1 5
/ \ / \
0 2 4 6
---------------------cut---------------------
3
/ \
1 5
/ \ / \
0 2 4 6
\
7
---------------------cut---------------------
3
/ \
1 5
/ \ / \
0 2 4 7
/ \
6 8
---------------------cut---------------------
3
/ \
1 7
/ \ / \
0 2 5 8
/ \ \
4 6 9
---------------------cut---------------------
REF:
1,http://blog.csdn.net/jkay_wong/article/details/6676488
2,数据结构(C语言版) Ellis Horowitz