C++实现二叉平衡树AVL的节点合并与分裂算法 _ 高度平衡维护核心【源码】

落萱吖_2536

落萱吖_2536

2026-05-14

264人浏览

原创

avl树节点分裂与合并需额外设计结构重组机制:分裂将超限节点按中位键拆为两子节点并上移中位键,合并吸收低键数兄弟节点,均需更新高度、平衡因子并触发旋转修复;双旋处理复合失衡;高度缓存须严格维护;并发时需细粒度锁与迭代器安全防护。

c++实现二叉平衡树avl的节点合并与分裂算法 _ 高度平衡维护核心【源码】

如果您在C++中实现AVL树时需要支持节点合并与分裂操作,以维持整棵树的高度平衡性,则必须在标准插入/删除逻辑之外,额外设计满足AVL平衡因子约束的结构重组机制。以下是实现该功能的核心步骤:

一、AVL节点分裂:当单节点存储键值超限触发水平切分

分裂操作用于处理一个AVL节点内部键集合过大(例如扩展为B+树风格多键节点)后需按中位键拆分为两个子节点,并将中位键上移至父节点。此过程需同步更新各节点高度与平衡因子,确保分裂后子树仍满足|height(left) − height(right)| ≤ 1。

1、定位待分裂节点,提取其有序键值数组K[0..m]及对应子树指针数组C[0..m](m ≥ MAX_DEGREE−1)。

2、取中位索引mid = m / 2,将K[0..mid−1]与C[0..mid]封装为新左节点,K[mid+1..m]与C[mid+1..m+1]封装为新右节点。

3、将K[mid]作为提升键,构造新父节点条目,并将左、右节点设为其左右子指针。

4、递归向上更新从新父节点到根路径上所有节点的高度字段,对每个节点重新计算balance = height(left) − height(right)。

5、若某祖先节点balance值变为2或−2,则立即在其子树内执行对应LL/LR/RR/RL旋转,并继续向上校验平衡性。

二、AVL节点合并:当两兄弟节点键数过少触发垂直吸收

合并操作适用于左右子节点键数量均低于最小阈值(如MIN_KEYS = ⌊(MAX_DEGREE−1)/2⌋)的情形,此时将二者键集、子树指针与中间父键整合为单一节点,并释放原兄弟节点内存。该操作可能降低父节点度数,需向上传导检查是否触发进一步合并或旋转。

1、确认当前父节点P存在且其左右子节点L与R的总键数 + 1(父键) ≤ MAX_DEGREE−1。

2、创建临时键数组:合并L.keys、P.key、R.keys为有序序列;合并L.children、R.children为新子树指针数组。

3、用该键数组与指针数组构造全新节点N,其height = max(L.height, R.height) + 1。

4、将P的父节点中指向L或R的指针替换为指向N,并删除L、R及P节点。

5、沿父链向上回溯,对每个受影响祖先节点重新计算height与balance;若出现balance = ±2,执行对应单/双旋转修复并终止向上更新。

三、双旋结构嵌入:LR型与RL型分裂/合并中的原子平衡操作

在分裂导致右子树过高、或合并引发左子树失衡等复合场景中,仅单旋无法恢复AVL条件,必须调用预定义的双旋函数。此类操作本质是两次单旋的组合,但需保证中间状态不破坏BST性质且高度更新精确到每层。

C++14
C++14

C++14 对 C++11 的修正与增强版本,适合旧系统维护和较老工具链兼容。

下载

1、识别失衡类型:若parent.balance == 2且left_child.balance == −1,则为LR型;若parent.balance == −2且right_child.balance == 1,则为RL型。

2、对LR型:先对left_child执行左旋,再对parent执行右旋;对RL型:先对right_child执行右旋,再对parent执行左旋。

3、每次旋转后立即更新涉及三个节点(旋转中心、原父、原孙)的高度字段,公式为height = max(left→height, right→height) + 1。

4、旋转完成后,将parent.balance重置为0,left_child与right_child的balance依新子树结构重算,确保所有balance ∈ {−1, 0, 1}。

四、高度缓存一致性维护:分裂与合并中的O(1)高度更新策略

为避免每次操作后遍历子树求高,每个AVL节点须显式存储height成员。分裂与合并过程中,仅路径上被修改的节点需重算height,其余节点保持不变。关键在于旋转与键迁移时严格遵循“先更新子节点height,再更新父节点height”的顺序。

1、在节点构造函数中初始化height = 1;空子树指针对应height = 0。

2、每次子树指针变更(如旋转中child赋值、合并中children数组重排),必须同步触发对应子节点height读取。

3、计算新height时使用max()而非递归调用get_height(),防止重复计算;例如new_height = std::max(l ? l->height : 0, r ? r->height : 0) + 1。

4、所有对外接口(insert/delete/split/merge)返回前,验证根节点height字段与实际最大深度一致,若不一致则抛出std::runtime_error("height cache corrupted")。

五、键冲突与迭代器失效防护:分裂合并期间的线程安全边界

当AVL树支持并发访问时,分裂与合并属于非原子结构变更,必须通过细粒度锁或RCU机制隔离。即使单线程环境,也需防止用户持有失效node*或iterator在操作中途被释放。

1、在split入口处对目标节点及其父节点加独占锁;merge操作需同时锁定父节点、左右子节点共三个节点。

2、所有对外暴露的迭代器(如avl_iterator)内部存储weak_ptr而非裸指针,dereference时检查lock()是否非空。

3、在节点析构前调用unregister_from_ancestors(),清除所有上级节点中对该节点的指针引用缓存。

4、提供split_safe()与merge_safe()包装函数,自动捕获异常并在失败时回滚已分配内存,确保noexcept强异常安全保证。

C++免费学习笔记(深入):立即使用
在学习笔记中,你将探索 C++ 的入门与实战技巧!

相关文章

PHP速学视频免费教程(入门到精通)
PHP速学视频免费教程(入门到精通)

PHP怎么学习?PHP怎么入门?PHP在哪学?PHP怎么学才快?不用担心,这里为大家提供了PHP速学教程(入门到精通),有需要的小伙伴保存下载就能学习啦!

下载

相关标签:

c++

本站声明:本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn

相关专题

更多
c++和c语言的区别有哪些
c++和c语言的区别有哪些

c++和c语言的区别:1、面向对象编程(OOP)支持不同;2、新增特性不同;3、标准库不同;4、编译方式不同;5、命名空间不同等等。想了解更多c++的相关内容,可以阅读本专题下面的文章。

2024.03.14

2248

9

c++和python学习顺序推荐
c++和python学习顺序推荐

一般建议先学习C++,再学习Python,因为这样可以逐步从较为底层的编程语言向更高级的语言过渡。想了解更多python的相关内容,可以阅读本专题下面的文章。

2024.03.14

1039

6

python和c++学习性价比分析
python和c++学习性价比分析

Python易于学习,广泛应用于Web开发、数据科学和人工智能等领域,但性能较低。C语言性能高,适用于对性能要求较高的场景,如游戏开发和系统编程,但学习曲线陡峭,错误处理复杂。想了解更多python的相关内容,可以阅读本专题下面的文章。

2024.03.14

447

5

c语言和c++一样吗
c语言和c++一样吗

c语言和c++是两种不同的编程语言,虽然有相似之处,但存在显著差异。c语言专注于过程式编程和系统级开发,以简洁、高效著称。c++作为c语言的超集,引入了面向对象编程,增强了代码组织和管理能力,但学习曲线也更陡峭。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

2024.03.14

327

5

c语言和c++先学哪个好
c语言和c++先学哪个好

初学者选择学习c语言还是c++语言,需要根据个人学习目标、背景以及编程兴趣和预期应用方向来决定。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

2024.03.14

426

5

c语言和c++的区别和联系
c语言和c++的区别和联系

c语言和c++是计算机科学领域应用广泛的编程语言。虽然它们有着相似的基础,但它们在语言类型、语法功能和内存管理方面存在着显著差异。本专题为大家提供相关的文章、下载、课程内容,供大家免费下载体验。

2024.03.14

600

5

c++软件中文更改教程
c++软件中文更改教程

对于 ide,可通过打开设置,找到语言设置,选择中文,并保存更改。对于非 ide 应用程序,可查找设置或选项,选择语言设置,更改为中文,并保存更改。想了解更多c++的相关内容,可以阅读本专题下面的文章。

2024.03.21

1429

9

python和java和c++学习性价比分析
python和java和c++学习性价比分析

Python以其易学性、丰富的库和活跃的社区而著称,适合数据科学、人工智能和Web开发。Java以其跨平台性、企业级应用开发和Android应用开发而闻名。C++以其底层控制能力、高效性能和游戏开发而著称。选择哪种语言取决于个人兴趣、职业方向和特定需求。想了解更多python和java和c++的相关内容,可以阅读本专题下面的文章。

2024.03.22

1237

7

c++和c语言学习顺序推荐
c++和c语言学习顺序推荐

对于初学者,建议先学习C语言,掌握编程基础后再转入C++,便于理解面向对象编程概念。有编程经验者可直接学习C++,快速接触高级编程技术。想了解更多c++和c语言的相关内容,可以阅读本专题下面的文章。

2024.03.25

1325

9

热门下载

更多
网站特效
/
网站源码
/
网站素材
/
前端模板

精品课程

更多
相关推荐
/
热门推荐
/
最新课程
C++ Core Guidelines
C++ Core Guidelines

共0课时 | 0人学习

C++ Reference
C++ Reference

共0课时 | 0人学习

C++ 官方标准说明
C++ 官方标准说明

共0课时 | 0人学习