数据结构 -- 树形查找(二)平衡二叉树

平衡二叉树

定义

平衡二叉树(AVL树) -- 树上的任意一点的左子树和右子树的高度之差不超过1

节点的平衡因子 = 左子树高-右子树高

平衡二叉树的结点的平衡因子的值只可能是-1、0、1

c 复制代码
//平衡二叉树结点
typedef struct AVLNode{
    int key;		//数据域
    int balance;	//平衡因子
    struct AVLNode *lchild,*rchild;
}AVLNode,*AVLTree;
插入操作

在插入新结点后,如何保持平衡

从插入点往回找到第一个不平衡的结点,调整以该结点为根结点的子树

每次调整的对象都是"最小不平衡子树"

插入新结点后如何调整"不平衡"问题(重点 选择手算处理)

LL -- 右单旋转(右旋)

RR -- 左单旋转(左旋)

代码思路:

LR -- 先左后右双旋转

RL -- 先右后左双旋转

【思考】为什么只需要调整最小不平衡子树?

插入操作导致"最小不平衡子树"高度+1,经过调整之后高度恢复,从而其他祖先节点都会恢复平衡

查找效率分析

若树高为h,则最坏情况下,查找一个关键字最多需要对比h次,即查找操作的时间复杂度不肯超过O(h)

平衡二叉树 -- 树上任一结点的左子树和右子树的高度之差不超过1

假设以nh表示深度为h的平衡树中含有的最少结点数

则有n0=0,n1=1,n2=2,并且有nh=n(h-1)+n(h-2)+1

hmax=O(log2n)

平衡二叉树的平均查找长度为O(log2n)

平衡二叉树的插入&删除

平衡二叉树的插入操作

​ 插入新结点后,要保持二叉排序树的特性不变

​ 若插入新结点导致不平衡,则需要调整平衡

平衡二叉树的删除操作

​ 删除新结点后,要保持二叉排序树的特性不变

​ 若删除结点导致不平衡,则需要调整平衡

具体步骤

①删除结点,方法同"二叉排序树"

②找最小不平衡子树(不存在则结束)
③在最小不平衡子树下,找到最高的儿子结点和孙子节点

④基于孙子结点的位置,调整平衡(LL/RR/LR/RL)

孙子 在LL:儿子右单旋转

孙子在RR:儿子左单旋转

孙子在LR:孙子先左旋后右旋

孙子在RL:孙子先右选后左旋

⑤如果不平衡向上传导,返回②

对最小不平衡子树的旋转可能导致树变矮从而导致上层祖先不平衡(不平衡只会向上传导)

平衡二叉树删除操作的时间复杂度=O(log2n)

相关推荐
嵌入式@秋刀鱼4 小时前
《第四章-筋骨淬炼》 C++修炼生涯笔记(基础篇)数组与函数
开发语言·数据结构·c++·笔记·算法·链表·visual studio code
嵌入式@秋刀鱼4 小时前
《第五章-心法进阶》 C++修炼生涯笔记(基础篇)指针与结构体⭐⭐⭐⭐⭐
c语言·开发语言·数据结构·c++·笔记·算法·visual studio code
泽02024 小时前
C++之list的自我实现
开发语言·数据结构·c++·算法·list
物联网嵌入式小冉学长7 小时前
2.线性表的链式存储-链表
数据结构·链表
顾小玙7 小时前
前缀和:leetcode974--和可被K整除的子数组
数据结构·算法
W说编程8 小时前
算法导论第三章:数据结构艺术与高效实现
c语言·数据结构·算法
hn小菜鸡8 小时前
LeetCode 2917.找出数组中的K-or值
数据结构·算法·leetcode
yield-bytes10 小时前
Java并发进阶系列:深度讨论高并发跳表数据结构ConcurrentSkipListMap的源代码实现(上)
数据结构
好易学·数据结构10 小时前
可视化图解算法51:寻找第K大(数组中的第K个最大的元素)
数据结构·python·算法·leetcode·力扣·牛客网·堆栈
NULL指向我11 小时前
C语言数据结构笔记5:Keil 编译器优化行为_malloc指针内存分配问题
c语言·数据结构·笔记