【数据结构】实现平衡二叉树的各种算法(插入,删除,查找,输出)

本文详细介绍了平衡二叉树(AVL树)的概念、存储结构以及各种操作的接口,包括插入、删除、查找、输出等算法。文章通过实例解释了如何维护平衡二叉树的平衡,以及处理不平衡时的旋转调整策略。


前言

       首先,博主写这篇文章出于一个目的,就是可以给真心想弄清平衡二叉树的同学一个引导,为什么这样说呢?首先,当今市面上关于数据结构的书讲的都是比较浅显,像平衡二叉树这个知识点一般就只讲了插入算法,极少书籍对平衡二叉树的删除算法进行讲解,所以对于很多朋友来说都很烦恼;其次,网上的资料关于平衡二叉树的算法讲解的也比较少(或者说是很多算法都是有错误的,至少我还没有找到一篇正确的关于平衡二叉树删除算法的代码)。那么,博主下面就给大家讲解平衡二叉树的各种算法,有什么错误也希望大家指出来。


一、定义

    我们都知道,一棵二叉查找树要达到性能最优,树形应该是层数越少越好。最理想的二叉树是高度达到最小的二叉树,包括满二叉树和完全二叉树。这一类二叉树在插入或者删除之后维持高度最毒最小的代价较大,故可以使用一种折中方案,即平衡二叉树。

         平衡二叉查找树(Balanced Binary Sort Tree,BBST)简称平衡二叉树。平衡二叉树有很多种,其中最著名的是由前苏联数学家Adelse-Velskil 和 Landis 在1962年提出的高度平衡的二叉树,根据科学家的英文名字首字母故平衡二叉树也可简称为AVL树。

        平衡二叉树或者是棵空树,或者是具有下列性质的二叉查找树:它的左子树和右子树都是平衡二叉树,且左子树和右子树的高度之差的绝对值不超过1。故将二叉树结点的平衡因子(Balance Factor)定义为该结点的左子树的高度减去它的右子树的高度,则平衡二叉树上所有结点的平衡因子只可能为-1,0,1。只要二叉树上有一个结点的平衡因子的绝对值大于1,那么这棵平衡二叉树就失去了平衡。


二、存储结构

typedef int RcdType;  
typedef int Status;  //Status就是int

/*平衡二叉树结构体*/
typedef struct BBSTNode{
    RcdType data;      //我自己定义RcdType就是int类型
    int bf;            //平衡因子
    BBSTNode *lchild, *rchild;   //左右孩子
}BBSTNode,*BBSTree;</span>


三、接口

 (1)根据输入字符串创建一棵平衡二叉树
   BBSTree MakeBBSTree();  
 (2)平衡二叉树插入元素操作
   Status InsertAVL(BBSTree &T, RcdType e, Status &taller);
 (3)平衡二叉树删除元素操作
    Status DeleteAVL(BBSTree &t, RcdType e, Status &shorter);
 (4)平衡二叉树查找元素操作
    BBSTree SearchAVL(BBSTree T, RcdType e);  
 (5)求平衡二叉树的深度
    int BBSTreeDepth(BBSTree T);
 (6)交换所有结点的左右子树
    void ExchangeSubTree(BBSTree &T)
 (7)递归先序遍历
    Status PreOrder_RecTraverse(BBSTree T);
 (8)递归中序遍历
    Status InOrder_RecTraverse(BBSTree T);
 (9)递归后序遍历
    Status LastOrder_RecTraverse(BBSTree T);
(10)非递归先序遍历
    void PreOrderTraverse_I(BBSTree T);
(11)非递归中序遍历
    void InOrderTraverse_I(BBSTree T);
(12)非递归后序遍历
    void LastOrderTraverse_I(BBSTree T);
(13)层次遍历输出二叉树
   void LevelOrederTraverse_Print(BBSTree T);
(14)括号表示法输出二叉树
   void BraNotationPrint(BBSTree T);


四、接口的实现及其算法

(1)根据输入字符串创建一棵平衡二叉树

       实现功能:根据输入的数字序列创建生成一棵平衡二叉树。例如输入(1 2 3 4 5 6 7回车),然后就会生成一个由1 2 3 4 5 6 7组成的平衡二叉树。主要思想是将 输入的序列用存放到一个动态数组(或者说是链表),通过GetInputToArray()函数来将输入的序列转换为数组,然后逐个读取数组中的元素调用Status InsertAVL(BBSTree &T, RcdType e, Status &taller)函数逐个插入到T中。

        初始条件:无

        返回值:返回一棵平衡二叉树

        调用函数:    Array GetInputToArray();/*获取输入存到数组a*/

                            Status InsertAVL(BBSTree &T, RcdType e, Status &taller); /*平衡二叉树的插入操作*/

/*根据输入的字符串建一棵平衡二叉树*/
BBSTree MakeBBSTree( ){
    int i=0;
    Status taller = TRUE;  
    BBSTree T = NULL;
    Array a;
    a = <strong>GetInputToArray();</strong>
    while(a!=NULL){
        taller = TRUE;
        <strong>InsertAVL(T, a->data, taller);</strong>
        a = a->next;
    }
    return T;
}


<span style="font-size:12px;">/*获取输入存到数组a*/
Array GetInputToArray(){
    Array head, p, q;
    char k;
    head = p = q = NULL;
    in
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值