当前位置: 首页 > news >正文

AVL树的四种旋转操作用于在插入或删除节点导致二叉树失去平衡

一、平衡二叉树(AVL 树)
设计目的:保证二叉排序树的高度为 $ O(\log_2 n) $,使插入、删除、查找等操作的最坏时间复杂度稳定在 $ O(\log_2 n) $。普通二叉排序树在极端情况下可能退化为链表,导致操作时间复杂度上升至 $ O(n) $。

核心定义:

  • 满足BST 性质:即对于任意节点,左子树所有节点值小于根节点值,右子树所有节点值大于根节点值。
  • 平衡条件:任一节点的左右子树高度差(称为平衡因子)的绝对值不超过 1。平衡因子 = 左子树深度 - 右子树深度,其值只能是 -1、0 或 1。

高度特性:
含有 $ n $ 个节点的 AVL 树,其最大高度约为 $ 1.44 \log_2 n $,远优于最坏情况下的 $ O(n) $,接近完全二叉树的理想高度 $ \log_2 n $。

为了维持平衡,在插入或删除节点后若出现不平衡(平衡因子变为 ±2),需通过旋转操作(单旋:LL、RR;双旋:LR、RL)进行调整,恢复平衡。


二、线索二叉树(Threaded Binary Tree)
设计目的:解决普通二叉树中无法高效获取某节点在中序遍历中的前驱和后继的问题。同时利用原本浪费的空指针域(n 个节点共有 $ n+1 $ 个空指针)来存储有用的线索信息,提高空间利用率和遍历效率。

实现方式:

  • 将空的左指针改为指向该节点在中序遍历中的前驱节点。
  • 将空的右指针改为指向该节点在中序遍历中的后继节点。
  • 引入两个标志位:
    • ltag:0 表示左指针指向左孩子,1 表示左指针为线索,指向前驱。
    • rtag:0 表示右指针指向右孩子,1 表示右指针为线索,指向后继。

节点结构示例(C语言风格):

structBTnode{intdata;structBTnode*left,*right;intltag;// 0: child, 1: thread (predecessor)intrtag;// 0: child, 1: thread (successor)};

通过中序线索化后,可以不使用栈或递归实现高效的中序遍历,直接沿线索访问下一个节点。
AVL树的四种旋转操作用于在插入或删除节点导致二叉树失去平衡(即某个节点的平衡因子变为±2)时,恢复其平衡性。这些旋转操作根据失衡节点与其子树中“过高”部分的位置关系分为四类:LL、RR、LR、RL。


一、四种旋转类型及适用场景

类型全称触发条件(以失衡节点为z场景描述
LL型Left-Leftz 的左子树比右子树高 2,且 z 的左孩子(y)的左子树更高(平衡因子为 +1 或 +2)失衡路径连续向左,形成“左偏左”结构
RR型Right-Rightz 的右子树比左子树高 2,且 z 的右孩子(y)的右子树更高(平衡因子为 -1 或 -2)失衡路径连续向右,“右偏右”结构
LR型Left-Rightz 的左子树过高,但 z 的左孩子的右子树更高先左后右的“Z”字形结构
RL型Right-Leftz 的右子树过高,但 z 的右孩子的左子树更高先右后左的镜像“Z”字形

📌核心思想:通过一次或两次旋转将“过高”的中间节点提升为新的根,使树重新满足 AVL 平衡条件。


二、旋转操作实现(C语言风格)

假设节点结构如下:

typedefstructAVLNode{intdata;structAVLNode*left;structAVLNode*right;intheight;// 存储当前节点高度,便于计算平衡因子}AVLNode;

辅助函数:获取高度与平衡因子

intmax(inta,intb){return(a>b)?a:b;}intheight(AVLNode*node){returnnode==NULL?0:node->height;}intgetBalance(AVLNode*node){returnnode==NULL?0:height(node->left)-height(node->right);}
1.右单旋(LL旋转)

适用于 LL 型失衡。

AVLNode*rotateRight(AVLNode*y){AVLNode*x=y->left;AVLNode*T2=x->right;// 执行右旋x->right=y;y->left=T2;// 更新高度(先更新子节点,再更新父节点)y->height=max(height(y->left),height(y->right))+1;x->height=max(height(x->left),height(x->right))+1;returnx;// 新的根节点}
2.左单旋(RR旋转)

适用于 RR 型失衡。

AVLNode*rotateLeft(AVLNode*x){AVLNode*y=x->right;AVLNode*T2=y->left;// 执行左旋y->left=x;x->right=T2;// 更新高度x->height=max(height(x->left),height(x->right))+1;y->height=max(height(y->left),height(y->right))+1;returny;// 新的根节点}
3.左右双旋(LR旋转)

先对左孩子左旋(RR),再对根右旋(LL)。

AVLNode*rotateLeftRight(AVLNode*z){z->left=rotateLeft(z->left);// 左孩子做一次左旋(RR)returnrotateRight(z);// 再整体右旋(LL)}
4.右左双旋(RL旋转)

先对右孩子右旋(LL),再对根左旋(RR)。

AVLNode*rotateRightLeft(AVLNode*z){z->right=rotateRight(z->right);// 右孩子做一次右旋(LL)returnrotateLeft(z);// 再整体左旋(RR)}

三、插入后的平衡调整逻辑示例

AVLNode*insert(AVLNode*node,intdata){// 1. 标准BST插入if(node==NULL){AVLNode*newNode=(AVLNode*)malloc(sizeof(AVLNode));newNode->data=data;newNode->left=newNode->right=NULL;newNode->height=1;returnnewNode;}if(data<node->data)node->left=insert(node->left,data);elseif(data>node->data)node->right=insert(node->right,data);elsereturnnode;// 不允许重复值// 2. 更新当前节点高度node->height=max(height(node->left),height(node->right))+1;// 3. 获取平衡因子intbalance=getBalance(node);// 4. 判断失衡类型并旋转调整// LL型if(balance>1&&data<node->left->data)returnrotateRight(node);// RR型if(balance<-1&&data>node->right->data)returnrotateLeft(node);// LR型if(balance>1&&data>node->left->data){node->left=rotateLeft(node->left);returnrotateRight(node);}// RL型if(balance<-1&&data<node->right->data){node->right=rotateRight(node->right);returnrotateLeft(node);}returnnode;// 已平衡,返回原节点}

总结记忆口诀

  • “同方向用单旋”:LL → 右旋,RR → 左旋
  • “异方向用双旋”:LR → 先左旋左孩子,再右旋根;RL → 先右旋右孩子,再左旋根
http://www.jsqmd.com/news/88221/

相关文章:

  • vue基于Spring Boot框架学生健康饮食与运动管理系统_c3g9i4f9
  • *SPOOLing 技术(假脱机技术)** - 全称:Simultaneous Peripheral Operations On-Line(外部设备同时联机操作)
  • 超声相控阵全聚焦算法 Comsol超声全矩阵仿真模型(仿真模型可以获得全矩阵数据)
  • 17、Debian系统管理基础与实用工具介绍
  • 量子软件测试:我们准备好了吗?
  • 2026年最新教程!手把手教你用Python画一颗圣诞树(附源码)无需部署可直接运行!
  • 沉浸式LED显示屏LED电子屏多少钱
  • 在虚拟内存管理中,页面置换算法用于决定当物理内存满时,应将哪个页面换出
  • AI使用总结
  • 18、Debian 系统用户与认证管理全解析
  • 存储管理技术主要分为页式、段式和段页式三种,它们在内存空间的划分方式
  • 19、Debian 系统初始化与自动进程管理全解析
  • 【设计模式|第四篇】适配器模式:让不兼容的接口协同工作
  • 线程是进程内的独立调度单位,是CPU调度的基本单元
  • 20、Debian系统管理:备份与设备管理全解析
  • 终于有人把大模型讲明白了:LLM 从入门到精通全解析
  • 2025年行业内评价好的3A信用认证代办多少钱,3A信用认证/3A企业信用认证/企业信用等级认证3A信用认证代理怎么选择 - 品牌推荐师
  • **P(Bufferfull)**:表示执行 wait 操作(即信号量减 1),用于判断是否有产品可消费
  • 21、Linux 备份指南:保障数据安全的实用方法
  • QMS软件系统:质量成本直降40%,让质管变“智造“——全星质量管理QMS软件系统应用解析
  • 永生数字系统:与之配套的测试哲学
  • 自动化?先搞懂这几点
  • asgiref终极指南:高效解决Python异步通信难题
  • 16、Debian内核:管理、特性与定制全解析
  • 早停法(Early_Stopping)
  • 探索四种商品售货机:MCGS 7.7 与三菱 PLC 联机之旅
  • 突破性多模态架构革命:Qwen3-VL-235B-A22B-Instruct-FP8重塑视觉语言交互边界
  • 医学影像深度学习知识点总结
  • 如何快速定位某个域名(如 deepskai.cn)对应的部署配置与代码目录(CentOS 示例)
  • CentOS 8 中可以使用 **dnf**(yum 的继任者)来安装 Docker。