目录

一、概述

二、红黑树插入

三、总结


一、概述

红黑树是一颗二叉平衡树,并且查找不会破坏树的平衡,所以查找跟二叉平衡树的查找没有什么区别,可以看前面的文章进行学习,这里不再过多阐述。本节我们主要总结红黑树插入相关的知识。

二、红黑树插入

红黑树的插入包含两个步骤:

  • 在树中查找插入的位置;
  • 插入后自平衡;

查找流程:

  1. 从根节点开始查找;
  2. 若根节点为空,那么插入节点作为根节点,结束;
  3. 若根节点不为空,那么把根节点作为当前节点;
  4. 若当前节点为null,返回当前节点的父节点,结束;
  5. 若当前节点key等于查找key,那么该key所在节点就是插入节点,更新节点的值,结束;
  6. 若当前节点key大于查找key,把当前节点的左子节点设置为当前节点,重复步骤4;
  7. 若当前节点key小于查找key,把当前节点的右子节点设置为当前节点,重复步骤4;

经过上面几个步骤已经找到节点插入的位置了,把插入节点放到正确的位置就可以了。

注意:插入节点应该是红色。

原因:根据红黑树特性之一【任意一节点到每个叶子节点的路径都包含数量相同的黑节点】,红色在父节点(如果存在)是黑色节点时,红黑树的黑色平衡不会被破坏,所以不需要进行自平衡操作。但如果插入节点是黑色,那么插入位置所在的子树黑色节点总是多1,必须做自平衡操作。

红黑树插入分很多种情况:

【a】红黑树为空树

因为红黑树为空树,所以直接将插入节点作为红黑树的根节点,然后注意红黑树跟节点必须为黑色,所以还需要将插入节点的颜色变为黑色,这种情况是最简单的红黑树插入操作。

处理步骤总结:

  • 把插入节点作为根节点
  • 把节点设置为黑色

【b】插入节点的Key已存在

根据key值,在红黑树中查找已经存在相同key的节点,因为插入之前红黑树已经是平衡的,所以只需要将插入节点的颜色设置为已存在的相同key的节点的颜色,然后更新key值即可。

处理步骤总结:

  • 把插入节点设为当前节点的颜色;
  • 更新当前节点的值为插入节点的值;

【c】插入节点的父节点为黑节点

因为红黑树规定新插入节点的颜色为红色,当插入节点的父节点为黑色时,并不会破坏【任意一节点到每个叶子节点的路径都包含数量相同的黑节点】特性,所以无需进行平衡操作,直接插入即可。

处理步骤总结:

  • 无需进行平衡操作,直接插入新节点

【d】插入节点的父节点为红节点

这种情况是最复杂的,因为红黑树规定新插入节点的颜色为红色,当插入节点的父节点为红色时,必然就破坏了【任意一节点到每个叶子节点的路径都包含数量相同的黑节点】特性,所以这种情况必须进行自平衡操作。

这种情况也分为下面好几种场景:

  • 【d-1】叔叔节点存在并且为红节点;
  • 【d-2】叔叔节点不存在或为黑节点,并且插入节点的父亲节点是祖父节点的左子节点;

【d-1】叔叔节点存在并且为红节点【叔叔节点:S 插入节点:I 父节点:P 祖父节点:PP】

从红黑树【每个红色节点的两个子节点一定都是黑色】特性可以推测出插入节点的祖父节点PP肯定为黑节点,因为不可以同时存在两个相连的红节点。那么此时该插入子树的红黑层数的情况是:黑红红。最简单的处理方式是把其改为:红黑红。

示意图如下所示:

可见,插入节点的祖父节点PP已经是红色节点,如果PP的父节点是黑色,那么满足【不能存在相连的两个红色节点】特性;如果PP的父节点是红色,那么PP红色,PP父节点也是红色,又得从PP节点出发,继续进行插入自平衡操作,一直到红黑树平衡为止。

【d-2】叔叔节点不存在或为黑节点,并且插入节点的父亲节点是祖父节点的左子节点【叔叔节点:S 插入节点:I 父节点:P 祖父节点:PP】

如果叔叔节点为黑节点,而父节点为红节点,那么叔叔节点所在的子树的黑色节点就比父节点所在子树的多1了,这不满足红黑树【任意一节点到每个叶子节点的路径都包含数量相同的黑节点】特性。下图也可以看出不满足:

【d-2】又可以分为如下两种:

  • 【d-2-1】插入节点是其父节点的左子节点;
  • 【d-2-2】插入节点是其父节点的右子节点;

【d-2-1】插入节点是其父节点的左子节点

处理步骤总结:

  • P设置为黑色
  • PP设置为红色
  • 对PP节点进行右旋

【d-2-2】插入节点是其父节点的右子节点

处理步骤总结:

  • 对P节点进行左旋操作就得到上面一种情况【d-2-1】【插入节点是其父节点的左子节点】
  • I设置为黑色
  • PP设置为红色
  • 对PP节点进行右旋

【d-3】叔叔节点不存在或为黑节点,并且插入节点的父亲节点是祖父节点的右子节点

【d-3】可以分为如下两种情况:

  • 【d-3-1】插入节点是其父节点的右子节点
  • 【d-3-2】插入节点是其父节点的左子节点

【d-3-1】插入节点是其父节点的右子节点

处理步骤总结:

  • P设置为黑色
  • PP设置为红色
  • 对PP节点进行左旋

【d-3-2】插入节点是其父节点的左子节点

处理步骤总结:

  • 对P节点进行右旋操作就得到上面一种情况【d-3-1】【插入节点是其父节点的右子节点】
  • I设置为黑色
  • PP设置为红色
  • 对PP节点进行左旋

三、总结

本篇文章主要总结了红黑树插入的四种情况,其中前三种情况都比较好理解,第四种情况比较复杂,需要好好画图才能理解的好一些,附上笔者关于红黑树插入的脑图总结:

由于笔者水平有限,文中可能存在不对之处,还望大家指正,一起学习,一起进步!

数据结构之红黑树插入详解相关推荐

  1. 红黑树操作详解——很形象的过程

    红黑树是一种很好的自平衡二叉排序树,在此,给出一个网友给出的红黑树操作详解: https://segmentfault.com/a/1190000012728513 里面给出了红黑树的详细操作,过程很 ...

  2. 红黑树原理详解及golang实现

    红黑树原理详解及golang实现 文章目录 红黑树原理详解及golang实现 二叉查找树 性质 红黑树 性质 operation 红黑树的插入 `情形1`:空树 `情形2`:插入节点父节为黑色, `情 ...

  3. STL源码剖析---红黑树原理详解上

    转载请标明出处,原文地址:http://blog.csdn.net/hackbuteer1/article/details/7740956 一.红黑树概述 红黑树和我们以前学过的AVL树类似,都是在进 ...

  4. STL源码剖析---红黑树原理详解

    红黑树概述 红黑树都是在进行插入和删除时通过特定操作保持二叉查找树的平衡,从而获得较高的查找性能.红黑树追求的时局部平衡而不是AVL树中的非常严格的平衡. 所谓红黑树,不仅是一个二叉搜索树,而且必须满 ...

  5. STL源码剖析---红黑树原理详解下

    转载请标明出处,原文地址:http://blog.csdn.net/hackbuteer1/article/details/7760584       算法导论书上给出的红黑树的性质如下,跟STL源码 ...

  6. 红黑树原理详解及代码实现

    文章目录 1. 红黑树概念 2. 节点定义 3. 旋转操作 4. 插入操作 5. 删除操作 6. 完整代码 1. 红黑树概念 下图就是一棵红黑树: 为了后续操作中不出现空指针异常,可以加入一个额外的哨 ...

  7. 红黑树:节点插入详解及其红黑树自我实现

    红黑树:节点插入详解及其红黑树自我实现 红黑树的四个性质: 每个结点不是红色就是黑色 根节点是黑色的 如果一个节点是红色的,则它的两个孩子结点是黑色的 对于每个结点,从该结点到其所有后代叶结点的简单路 ...

  8. 底层实现红黑树_stl map底层之红黑树插入步骤详解与代码实现 | 学步园

    本篇文章并没有详细的讲解红黑树各方面的知识,只是以图形的方式对红黑树插入节点需要进行调整的过程进行的解释. 最近在看stl源码剖析,看到map底层红黑树的实现.为了加深对于红黑树的理解就自己动手写了红 ...

  9. 数据结构-红黑树插入结点示例

    数据结构-红黑树插入结点示例 1.红黑树简介 2.在线可视化生成红黑树工具 3.红黑树插入结点性质和规则 3.1.红黑树插入结点性质 3.2.红黑树插入结点规则 4.红黑树插入结点示例 4.1.红黑树 ...

  10. 内核数据结构之红黑树

    红黑树是一种自平衡的二叉查找树,是Linux主要的二叉树结构.红黑树有一个特殊的颜色属性,要么红色,要么黑色.红黑树通过强制以下条件来保证红黑树仍然是半平衡的. 所有结点要是红色或黑色的. 叶子结点是 ...

最新文章

  1. Python运维项目中用到的redis经验及数据类型
  2. P3366 【模板】最小生成树(链式前向星,prim,有坑)难度⭐⭐
  3. 使用Embedded VC++开发通讯终端及代码分析
  4. ubuntu 12.04lts 安装insight6.8a
  5. Xcode调试命令大全 (LLDB Cheatsheet)
  6. docker 容器运行 golang程序_「Docker」 - 运行 amp; 管理容器
  7. conda安装pytorch1.10.1+paddlepaddle-gpu2.2.1+cuda10.2+cudnn7.6.5
  8. 机器学习 Machine Learning中多元线性回归的学习笔记~
  9. js 一个关于图片onload加载的事
  10. Unity3D 2018安装教程
  11. [转载] 像 IDE 一样使用 vim
  12. 性能测试实战(二):性能测试基础
  13. 真的精采!AI赢了DOTA界的世界冠军 让人兴奋又纠结
  14. 研报复现系列(六)【国泰君安】基于CCK模型的股票市场羊群效应研究
  15. Spatial4j简介
  16. ubuntu18.04 LTS 安装英伟达驱动
  17. 组合数c(n,m)计算的四种方法
  18. DTOJ 4426. 爱乐之城
  19. POSIX标准是什么?
  20. ReactNative进阶(三十五):应用脚手架 Yo 构建 RN 页面

热门文章

  1. php 包含截断,php – 表单包含大量输入时截断/缺少表单...
  2. C/C++[ w1785]字符串连接
  3. 容器技术Docker K8s 34 容器服务ACK基础与进阶-安全管理
  4. 算法:翻转图片Rotate Image
  5. ValueError: The truth value of a Series is ambiguous. Use a.empty, a.bool(), a.item(), a.any()
  6. Regularized logistic regression(正则化逻辑回归)----吴恩达机器学习
  7. webfigure显示到网页上所踩过的坑--自写servlet
  8. 《Thumbs up? Sentiment Classification using Machine Learning Techniques》笔记
  9. ROS启动ASUS Xtion PRO LIVE摄像头
  10. python列表删除会出现一个错误 list index out of range