平衡二叉树 AVL

来源:互联网 发布:淘宝刀剑哪家好 编辑:程序博客网 时间:2024/05/17 01:22

笔记:
1、 在包含有n个结点的平衡树上查找的时间复杂度为 O(log n),深度也和O(log n)同数量级。
在平衡树上进行查找的过程和排序树相同,因此,在查找过程中和给定值进行比较的关键字个数不超过树的深度。
2、 二叉排序树又称为二叉查找树。
3、 平衡二叉树必须是二叉查找树。
4、 AVL树的查找、插入、删除操作在平均和最坏的情况下都是O(logn),这得益于它时刻维护着二叉树的平衡。如果我们需要查找的集合本身没有顺序,在频繁查找的同时也经常的插入和删除,AVL树是不错的选择。不平衡的二叉查找树在查找时的效率是很低的,因此,AVL如何维护二叉树的平衡是我们的学习重点。
注意:对于平衡因子的计算建议通过记录树的高度来计算比较方便,单纯的记录平衡因子会很麻烦。
推荐两个比较好的网址:
http://www.cnblogs.com/QG-whz/p/5167238.html
http://blog.csdn.net/whucyl/article/details/17289841
实现代码:

#include <iostream>#include <stdio.h>#include <malloc.h>#include <math.h>typedef int ATElemType;using namespace std;typedef struct ATNode{    ATElemType key;    int height;    struct ATNode *lChild;    struct ATNode *rChild;}ATNode, *AVLtree;///Get heightint GetHeight(AVLtree root){    if(root==NULL)        return 0;    else        return root->height;}///Update heightvoid updateHeight(AVLtree &root){    if(root!=NULL)        root->height=max(GetHeight(root->lChild),GetHeight(root->rChild))+1;}///LL型,右旋void rRotate(AVLtree &root){    ATNode *p=root->lChild;    root->lChild=p->rChild;    p->rChild=root;    updateHeight(root);    updateHeight(p);    root=p;}///RR型,左旋void lRotate(AVLtree &root){    ATNode *p=root->rChild;    root->rChild=p->lChild;    p->lChild=root;    updateHeight(root);    updateHeight(p);    root=p;}///LR型,左旋再右旋void LRrotate(AVLtree &root){    lRotate(root->lChild);    rRotate(root);}///RL型,右旋再左旋void RLrotate(AVLtree &root){    rRotate(root->rChild);    lRotate(root);}///插入节点--递归AVLtree insertElem_AVL(AVLtree &root,ATElemType eKey){    if(root!=NULL)    {        if(root->key==eKey)        {            return root;        }        else if(root->key>eKey)  //插在左子树上        {            root->lChild=insertElem_AVL(root->lChild,eKey);            updateHeight(root);            if(GetHeight(root->lChild)-GetHeight(root->rChild)==2)            {                if(GetHeight(root->lChild->lChild)>GetHeight(root->lChild->rChild))  //LL                    rRotate(root);                else  //LR                    LRrotate(root);            }        }        else //root->key<eKey  //插在右子树上        {            root->rChild=insertElem_AVL(root->rChild,eKey);            updateHeight(root);            if(GetHeight(root->lChild)-GetHeight(root->rChild)==-2)            {                if(GetHeight(root->rChild->rChild)>GetHeight(root->rChild->lChild))//RR                    lRotate(root);                else  //RL                    RLrotate(root);            }        }        return root;    }    else    {        root=(AVLtree)malloc(sizeof(ATNode));        root->key=eKey;        root->height=1;        root->lChild=root->rChild=NULL;        return root;    }}///求一棵树中的最大值点AVLtree maxValue_AVL(AVLtree root){    if(root!=NULL)    {        ATNode *p;        for(p=root;p->rChild!=NULL;p=p->rChild){}        return p;    }}///求一棵树中的最小值点AVLtree minValue_AVL(AVLtree root){    if(root!=NULL)    {        ATNode *p;        for(p=root;p->lChild!=NULL;p=p->lChild){}        return p;    }}///删除指定的元素AVLtree DeleteElem_AVL(AVLtree &root,ATElemType eKey){    if(root!=NULL)    {        if(root->key==eKey)        {            if(root->lChild==NULL&&root->rChild==NULL)            {                free(root);                root=NULL;                return root;            }            else if(root->lChild==NULL)            {                ATNode *p=root;                root=root->rChild;                free(p);                p=NULL;                return root;            }            else if(root->rChild==NULL)            {                ATNode *p=root;                root=root->lChild;                free(p);                p=NULL;                return root;            }            else  //左右子树均不为空            {                if(GetHeight(root->lChild)>=GetHeight(root->rChild))  //左子树高                {                    root->key=maxValue_AVL(root->lChild)->key;                    root->lChild=DeleteElem_AVL(root->lChild,root->key);                    updateHeight(root);                    if(GetHeight(root->rChild)-GetHeight(root->lChild)==2)//在左子树上删除结点相当于在右子树上插入节点                    {                        if(GetHeight(root->rChild->rChild)>GetHeight(root->rChild->lChild))                            lRotate(root);                        else                            RLrotate(root);                    }                }                else  //右子树高                {                    root->key=minValue_AVL(root->rChild)->key;                    root->rChild=DeleteElem_AVL(root->rChild,root->key);                    updateHeight(root);                    if(GetHeight(root->lChild)-GetHeight(root->rChild)==2)//在右子树上删除结点相当于在左子树上插入节点                    {                        if(GetHeight(root->lChild->lChild)>GetHeight(root->lChild->rChild))                            rRotate(root);                        else                            LRrotate(root);                    }                }                return root;            }        }        else if(root->key>eKey) //在左子树上        {            root->lChild=DeleteElem_AVL(root->lChild,eKey);            updateHeight(root);            if(GetHeight(root->rChild)-GetHeight(root->lChild)==2)//在左子树上删除结点相当于在右子树上插入节点            {                if(GetHeight(root->rChild->rChild)>GetHeight(root->rChild->lChild))                    lRotate(root);                else                    RLrotate(root);            }            return root;        }        else  //在右子树上        {            root->rChild=DeleteElem_AVL(root->rChild,eKey);            updateHeight(root);            if(GetHeight(root->lChild)-GetHeight(root->rChild)==2)//在右子树上删除结点相当于在左子树上插入节点            {                if(GetHeight(root->lChild->lChild)>GetHeight(root->lChild->rChild))                    rRotate(root);                else                    LRrotate(root);            }            return root;        }    }    else        return NULL;}///中序遍历void Inorder_AVL(AVLtree root){    if(root)    {        Inorder_AVL(root->lChild);        printf("%d ",root->key);        Inorder_AVL(root->rChild);    }}///前序遍历void PreOrder_AVL(AVLtree root){    if(root)    {        printf("%d ",root->key);        PreOrder_AVL(root->lChild);        PreOrder_AVL(root->rChild);    }}///后序遍历void PostOrder_AVL(AVLtree root){    if(root)    {        PostOrder_AVL(root->lChild);        PostOrder_AVL(root->rChild);        printf("%d ",root->key);    }}///查找元素---递归AVLtree searchElem_AVL(AVLtree root,ATElemType eKey){    if(root)    {        if(root->key==eKey)            return root;        else if(root->key>eKey)            searchElem_AVL(root->lChild,eKey);        else            searchElem_AVL(root->rChild,eKey);    }    else        return NULL;}///查找元素---非递归AVLtree searElemNoRecurse_AVL(AVLtree root,ATElemType eKey){    ATNode *p=root;    while(p)    {        if(p->key==eKey)            return p;        else if(p->key>eKey)            p=p->lChild;        else            p=p->rChild;    }    return NULL;}///销毁AVLvoid Destroy_AVL(AVLtree &root){    if(root)    {        Destroy_AVL(root->lChild);        Destroy_AVL(root->rChild);        free(root);        root=NULL;    }}int main(){    AVLtree mAVL=NULL;    //---test insert---    insertElem_AVL(mAVL,5);    insertElem_AVL(mAVL,8);    insertElem_AVL(mAVL,7);    insertElem_AVL(mAVL,2);    insertElem_AVL(mAVL,3);    insertElem_AVL(mAVL,4);    insertElem_AVL(mAVL,6);    insertElem_AVL(mAVL,9);    int height=GetHeight(mAVL);    printf("%d\n",height);    Inorder_AVL(mAVL);    printf("\n");    //--test delete---//    DeleteElem_AVL(mAVL,5);//    height=GetHeight(mAVL);//    printf("%d\n",height);//    Inorder_AVL(mAVL);//    printf("\n");//    printf("%d\n",mAVL->key);    //---test preOrder---//    PreOrder_AVL(mAVL);//    printf("\n");    //---test postOrder---//    PostOrder_AVL(mAVL);//    printf("\n");    //---test search(递归)---//    printf("%d\n",searchElem_AVL(mAVL,8)->key);    //---test search(非递归)---//    printf("%d\n",searElemNoRecurse_AVL(mAVL,6)->key);    //---test Destroy---    Destroy_AVL(mAVL);    printf("Test Destroy!\n");    return 0;}