笔记:
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 height
int GetHeight(AVLtree root)
{
if(root==NULL)
return 0;
else
return root->height;
}
///Update height
void 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;
}
///销毁AVL
void 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;
}