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

C++进阶--AVL树的实现续

文章目录

  • C++进阶--AVL树的实现
    • 双旋
    • AVL树的查找
    • AVL树的检验
    • 结语

很高兴和搭大家见面,给生活加点impetus,开启今天的比编程之路!!
在这里插入图片描述
今天我们来完善AVL树的操作,为后续红黑树奠定基础!!
作者:٩( ‘ω’ )و260
我的专栏:C++进阶,C++初阶,数据结构初阶,题海探骊,c语言
欢迎点赞,关注!!

C++进阶–AVL树的实现

在前面一个文章中,我们学习了AVL树插入情况的单旋,今天我们来学习双旋操作。

双旋

话不多说,我们直接来看具体的案例,左右双旋,请看下图:

来看这一种情况,此时如果我们是在5的左边进行插入操作的话,此时需要进行右单旋,以10为旋转中心,但是如果此时我们是在5的右边进行插入操作的话,如果我们继续进行单旋操作,就会发现这AVL树从左边高变成了右边高。
这种情况的时候,我们就应该进行双旋。

总结:什么时候使用单旋,什么时候使用双旋呢?
如果AVL树此时是一边高,即左边高的左边高或者是右边高的右边高,此时应使用单旋,但是如果是左边高的右边高或者是右边高的左边高,此时应该使用双旋

具体步骤:
需要用两次旋转才能解决,以5为旋转点进行⼀个左单旋,以10为旋转点进行一个右单旋,这棵树就平衡了。

我们再来看一个示例:
此时单旋是根本解决不了问题的。
在这里插入图片描述
注意观察:此时是左边高的右边高(相较于10来说,是左边高,相较于5来说,是右边高),应该使用双旋,我们来看一下具体过程。

过程:先以5为旋转点进行右单旋,随后再以10为旋转点进行右单旋。
具体图像在上方已经呈现,其实,当我们对5进行右单旋的时候,我们其实能够发现,这个时候已经是左单旋的模型了。
在这里插入图片描述

在这里插入图片描述

总结:为了方便记忆,我们来说明双旋之后造成的效果是什么?
我们发现8作为了新的根,5和10分别作为了8的左右子树,即旋转点作为了根的左右子树,以5左旋,5作为左子树,以10右旋,10作为了根的右子树。

接下来我们来看代码实现:

void RotateLR(Node* parent)//此时是左子树高,左子树的右子树高,因为LR,L在前
{//思路:先对subL进行左旋,再对parent进行右旋Node* subL = parent->_left;Node* subLR = subL->_right;int bf = subLR->_bf;RotateL(parent->_left);RotateR(parent);//int bf = subLR->_bf;//现在都已经修改了,还写在这里干嘛?//修改平衡因子if (bf == -1)//此时在subLR的左子树插入{subL->_bf = 0;parent->_bf = 1;subLR->_bf = 0;}else if (bf == 1)//此时在subLR的右子树插入{subL->_bf = -1;parent->_bf = 0;subLR->_bf = 0;}else if (bf == 0)//此时新插入的结点就是subLR,此时全部都为0{subL->_bf = 0;parent->_bf = 0;subLR->_bf = 0;}else {assert(false);}
}

当然,左右双旋是如此,右左双选也是如此。
接下来我们来看一下左右双旋的简图:
在这里插入图片描述

AVL树的查找

AVL树的查找,其实就是在寻找key需要放置的合适位置,其实本质上就是二叉搜索树搜索的过程。直接来看代码:

Node* Find(const K& key)//查找结点
{Node* cur = _root;while (cur){if (cur->_kv.first < key){cur = cur->_right;}else if (cur->_kv.first > key){cur = cur->_left;}else{return cur;}}return nullptr;
}

AVL树的检验

我们来看如果检验AVL树,检查AVL树需要检查平衡因子是否正常,其次就是高度差是否正常。检查平衡因子的话其实本质上就是检查高度差的问题。
直接设立两个变量,表示这个结点的左子树的高度和这个结点的右子树的高度。最后算一下高度差即可,随后再来算一下平衡因为是否能够对应上这个高度差即可
接下来我们直接来看代码实现:

bool _IsBalanceTree(Node* root)//检测这个二叉树是不是AVL树
{// 空树也是AVL树if (nullptr == root) return true;// 计算pRoot结点的平衡因⼦:即pRoot左右⼦树的⾼度差int leftHeight = _Height(root->_left);int rightHeight = _Height(root->_right);int diff = rightHeight - leftHeight;// 如果计算出的平衡因⼦与pRoot的平衡因⼦不相等,或者// pRoot平衡因⼦的绝对值超过1,则⼀定不是AVL树if (abs(diff) >= 2){cout << root->_kv.first << "⾼度差异常" << endl;return false;}if (root->_bf != diff){cout << root->_kv.first << "平衡因⼦异常" << endl;return false;}// pRoot的左和右如果都是AVL树,则该树⼀定是AVL树return _IsBalanceTree(root->_left) && _IsBalanceTree(root->_right);
}

结语

今天的内容就分享到这里,不足之处欢迎留言指正,感谢大家的支持!!
古之成大事者,不惟有超世之才,亦必有坚忍不拔之志!加油!!
在这里插入图片描述

相关文章:

  • MCP:让AI模型更可信的秘密武器
  • VRRP协议-IP地址冗余配置
  • Telnetlib三种异常处理方案
  • 微服务的“迷宫” - 我们为何需要服务网格?
  • 深入详解人工智能数学基础——微积分中的自动微分及其在PyTorch中的实现原理
  • 类加载机制详解:双亲委派模型与打破它的方式
  • MindSpore框架学习项目-ResNet药物分类-模型训练
  • 人脸真假检测:SVM 与 ResNet18 的实战对比
  • Yocto中的${D}解读
  • Android 13 默认打开 使用屏幕键盘
  • 使用FastAPI和Apache Flink构建跨环境数据管道
  • vue3项目中使用CodeMirror更复杂的用法,实现自定义语法模式,手动在指定光标位置插入/获取/替换/绑定文本
  • 达索MODSIM实施成本高吗?哪家服务商靠谱?
  • C++修炼:stack和queue
  • python校园新闻发布管理系统
  • 【Web】使用Vue3开发鸿蒙的HelloWorld!
  • uniapp-商城-51-后台 商家信息(logo处理)
  • Win 10 close AutoUpdate DataCollection
  • bash shell中readarray和mapfile的用法
  • DataBinding与Kotlin优化视图绑定
  • 江苏省委社会工作部部长等多人拟在省志愿服务联合会任职
  • 要更加冷静地看待“东升西降”的判断
  • 七大交响乐团在沪“神仙斗法”,时代交响奏出何等时代新声
  • 无人机穿越大理千年古塔落券洞内,涉事“飞手”被行拘10日
  • 万玲、胡春平调任江西省鹰潭市副市长
  • 金融监管局:已设立74支私募股权投资基金,支持投资科技创新企业