头文件

 typedef int ElementType;

 #ifndef _AVLTREE_H_
#define _AVLTREE_H_ struct AvlNode;
typedef struct AvlNode *Position;
typedef struct AvlNode *AvlTree; AvlTree MakeEmpty(AvlTree T);
Position Find(ElementType X, AvlTree T);
Position FindMin(AvlTree T);
Position FindMax(AvlTree T);
AvlTree Insert(ElementType X, AvlTree T);
AvlTree Delete(ElementType X, AvlTree T);
ElementType Retrieve(Position P);
void PrintTree(AvlTree T); #endif

源文件

 #include "fatal.h"
#include "avltree.h"
#include <malloc.h> struct AvlNode
{
ElementType Element;
AvlTree Left;
AvlTree Right;
int Height;
}; AvlTree MakeEmpty(AvlTree T) // 同二叉查找树
{
if(T != NULL) // 递归终止
{
MakeEmpty(T->Left);
MakeEmpty(T->Right);
free(T);
}
return T;
} Position Find(ElementType X, AvlTree T) // 同二叉查找树
{
if(T == NULL)
return NULL;
else if(X < T->Element)
{
return Find(X, T->Left);
}
else if(X > T->Element)
{
return Find(X, T->Right);
}
else
return T;
} Position FindMin(AvlTree T) // 递归实现
{
if(T == NULL)
return NULL;
else if(T->Left == NULL)
return T;
else
return FindMin(T->Left);
} Position FindMax(AvlTree T) // 非递归实现
{
if(T != NULL)
while(T->Right != NULL)
T = T->Right; return T;
} static int Height(Position P)
{
if(P == NULL)
return -; // 空树高度为-1
else
return P->Height;
} static int Max(int Left, int Right)
{
return Left > Right ? Left : Right;
} /* This function can be called only if K2 has a left child */
/* Perform a rotate between a node (K2) and its left child */
/* Update heights, then return new root */
static Position SingleRotateWithLeft(Position K2)
{
Position K1; K1 = K2->Left;
K2->Left = K1->Right;
K1->Right = K2; K2->Height = Max(Height(K2->Left), Height(K2->Right)) + ;
K1->Height = Max(Height(K1->Left), Height(K1->Right)) + ; return K1; /* New root */
} /* This function can be called only if K1 has a right child */
/* Perform a rotate between a node (K1) and its right child */
/* Update heights, then return new root */
static Position SingleRotateWithRight(Position K1)
{
Position K2; K2 = K1->Right;
K1->Right = K2->Left;
K2->Left = K1; K1->Height = Max(Height(K1->Left), Height(K1->Right)) + ;
K2->Height = Max(Height(K2->Left), Height(K2->Right)) + ; return K2; /* New root */
} /* This function can be called only if K3 has a left */
/* child and K3's left child has a right child */
/* Do the left-right double rotation */
/* Update heights, then return new root */
static Position DoubleRotateWithLeft(Position K3)
{
/* Rotate between K1 and K2 */
K3->Left = SingleRotateWithRight(K3->Left);
/* Rotate between K3 and K2 */
return SingleRotateWithLeft(K3);
} /* This function can be called only if K1 has a right */
/* child and K1's right child has a left child */
/* Do the right-left double rotation */
/* Update heights, then return new root */
static Position DoubleRotateWithRight(Position K1)
{
/* Rotate between K3 and K2 */
K1->Right = SingleRotateWithLeft(K1->Right);
/* Rotate between K1 and K2 */
return SingleRotateWithRight(K1);
} // 1. 找位置; 2. 插入; 3. 平衡性; 4. 旋转
AvlTree Insert(ElementType X, AvlTree T)
{
if(T == NULL)
{
/* Create and return a one-node tree */
T = (AvlTree)malloc(sizeof(struct AvlNode));
if(T == NULL)
FatalError("Out of space!");
else
{
T->Left = T->Right = NULL;
T->Height = ;
T->Element = X;
}
}
else if(X < T->Element)
{
T->Left = Insert(X, T->Left);
// 因为插到左边了, 所以肯定是左边比较高
if(Height(T->Left) - Height(T->Right) == )
{
if(X < T->Left->Element)
T = SingleRotateWithLeft(T);
else
T = DoubleRotateWithLeft(T);
}
}
else if(X > T->Element)
{
T->Right = Insert(X, T->Right);
// 插到右边了, 右边比较高
if(Height(T->Right) - Height(T->Left) == )
{
if(X > T->Right->Element)
T = SingleRotateWithRight(T);
else
T = DoubleRotateWithRight(T);
}
}
/* Else X is in the tree already; we'll do nothing */
T->Height = Max(Height(T->Left), Height(T->Right)) + ; return T;
} AvlTree Delete(ElementType X, AvlTree T)
{
printf( "Sorry; Delete is unimplemented; %d remains\n", X );
return T;
} ElementType Retrieve(Position P)
{
return P->Element;
} void PrintTree(AvlTree T)
{
if( T != NULL)
{
PrintTree(T->Left);
printf("%d ", T->Element);
PrintTree(T->Right);
}
}

测试文件

 #include "avltree.h"
#include <stdio.h> main( )
{
AvlTree T;
Position P;
int i;
int j = ; T = MakeEmpty( NULL );
for( i = ; i < ; i++, j = ( j + ) % )
T = Insert( j, T );
for( i = ; i < ; i++ )
if( ( P = Find( i, T ) ) == NULL || Retrieve( P ) != i )
printf( "Error at %d\n", i ); /* for( i = 0; i < 50; i += 2 )
T = Delete( i, T ); for( i = 1; i < 50; i += 2 )
if( ( P = Find( i, T ) ) == NULL || Retrieve( P ) != i )
printf( "Error at %d\n", i );
for( i = 0; i < 50; i += 2 )
if( ( P = Find( i, T ) ) != NULL )
printf( "Error at %d\n", i );
*/
printf( "Min is %d, Max is %d\n", Retrieve( FindMin( T ) ),
Retrieve( FindMax( T ) ) );
PrintTree(T);
return ;
}

[数据结构与算法] : AVL树的更多相关文章

  1. 数据结构与算法——AVL树类的C++实现

    关于AVL树的简单介绍能够參考:数据结构与算法--AVL树简单介绍 关于二叉搜索树(也称为二叉查找树)能够參考:数据结构与算法--二叉查找树类的C++实现 AVL-tree是一个"加上了额外 ...

  2. 数据结构和算法(Golang实现)(28)查找算法-AVL树

    AVL树 二叉查找树的树高度影响了查找的效率,需要尽量减小树的高度,AVL树正是这样的树. 一.AVL树介绍 AVL树是一棵严格自平衡的二叉查找树,1962年,发明者Adelson-Velsky和La ...

  3. 【数据结构】平衡二叉树—AVL树

    (百度百科)在计算机科学中,AVL树是最先发明的自平衡二叉查找树.在AVL树中任何节点的两个子树的高度最大差别为一,所以它也被称为高度平衡树.查找.插入和删除在平均和最坏情况下都是O(log n).增 ...

  4. 数据结构(三)实现AVL树

    AVL树的定义 一种自平衡二叉查找树,中面向内存的数据结构. 二叉搜索树T为AVL树的满足条件为: T是空树 T若不是空树,则TL.TR都是AVL树,且|HL-HR| <= 1 (节点的左子树高 ...

  5. 数据结构与算法分析-AVL树

    1.AVL树是带有平衡条件的二叉查找树. 2.AVL树的每个节点高度最多相差1. 3.AVL树实现的难点在于插入或删除操作.由于插入和删除都有可能破坏AVL树高度最多相差1的特性,所以当特性被破坏时需 ...

  6. 数据结构——二叉查找树、AVL树

    二叉查找树:由于二叉查找树建树的过程即为插入的过程,所以其中序遍历一定为升序排列! 插入:直接插入,插入后一定为根节点 查找:直接查找 删除:叶子节点直接删除,有一个孩子的节点删除后将孩子节点接入到父 ...

  7. [算法] avl树实现

    大二的时候数据结构课死活没看懂的一个东东,看了2小时,敲了2小时,调了2小时... 平衡树某一节点的左右子树高度相差大于1的时候即需要调整,调整可分为四中情况 ll,rr,lr,rl其中lr,rl是由 ...

  8. 数据结构与算法—Trie树

    Trie,又经常叫前缀树,字典树等等.它有很多变种,如后缀树,Radix Tree/Trie,PATRICIA tree,以及bitwise版本的crit-bit tree.当然很多名字的意义其实有交 ...

  9. Android版数据结构与算法(六):树与二叉树

    版权声明:本文出自汪磊的博客,未经作者允许禁止转载. 之前的篇章主要讲解了数据结构中的线性结构,所谓线性结构就是数据与数据之间是一对一的关系,接下来我们就要进入非线性结构的世界了,主要是树与图,好了接 ...

随机推荐

  1. ES 分布式搜索

    ES整个查询过程是scatter/gather的过程,具体如下: 图见 https://blog.csdn.net/thomas0yang/article/details/78572596?utm_s ...

  2. spring boot 学习(九)小工具篇:?秒防刷新

    注解 + 拦截器:?秒防刷新 小工具篇:工具许多都是我以前在 github 之类开源平台找到的小工具类,作者的信息什么的许多都忘了.先说声不好意思了.若有相关信息,麻烦提醒一下~ 解释 所谓的?秒防刷 ...

  3. 修改cmd窗口mysql的提示符:

    mysql提示符: \D  完整的日期 \d   当前数据库 \h    服务器地址 \u    当前用户 登录数据库的时候设置提示符:  mysql  -uroot  -proot  --promp ...

  4. Flash OS images to SD cards & USB drives & TF cards safely and easily using etcher

    install tools: wget https://github.com/resin-io/etcher/releases/download/v1.4.5/etcher-cli-1.4.5-lin ...

  5. js 禁止剪切、复制、粘贴的文本框代码

    有的网站中不允许用户复制.粘贴.剪切文本框中的内容的,是怎么实现的呢?看看下面的代码就知道了. <input id=”username” oncut=”return false” oncopy= ...

  6. JavaScript 自定义文本框光标——初级版

    文本框(input或textarea)的光标无法修改样式(除了通过color修改光标颜色).但笔者希望个人创建自己的网站时,文本框的光标有属于自己的风格.所以,尝试模拟文本框的光标,设计有自己风格的光 ...

  7. iOS9 http 不能连接的解决办法

    iOS9要求App内访问的网络必须使用HTTPS协议.原有的HTTP请求会报错,适配方法如下. 打开TARGETS-Build Phases, 添加New Run Script Phase,代码如下: ...

  8. WebGL编程指南案例解析之平移和旋转的math库实现

    这里说的math库实现,指的是,通过一般的加减乘除(角度计算)来更新坐标值. 因为涉及到坐标的变化,所以这里都是基于对顶点着色器的修改 平移: var vShader = ` attribute ve ...

  9. 无监督︱异常、离群点检测 一分类——OneClassSVM

    OneClassSVM两个功能:异常值检测.解决极度不平衡数据 因为之前一直在做非平衡样本分类的问题,其中如果有一类比例严重失调,就可以直接用这个方式来做:OneClassSVM:OneClassSV ...

  10. UI基础:target...action设计模式,手势识别器.UIimageview

    使用target..action和delegate设计模式可以实现解耦.使代码更加优化. 手势识别器: 手势识别器:是对触摸事件做了封装,无需自己去判断某个手势是否触发,手势识别器本身起到了识别作用, ...