红黑树:
注意:对于红黑规则3而言,如果节点是黑色的,则其子节点可以是红色也可以是黑色的。
-
为什么需要红黑树?
答:因为普通的二叉查找树会不平衡,甚至可能会退化为一个链表,如图所示:
但是链表的查找性能很差,我们希望一种数据结构在外面插入的时候可以动态的调整,使得左右子树高度相差不大,所以引出了红黑树。
-
C++ 已经提供了红黑树的模板类:#include <set> 、#include <map>
- set
- multiset
- map
- multimap
(是在std命名空间中的内容,所以要增加 using namespace std;)
-
举一个例子:
插入25,插入的结点都是红的,因为插入红色的结点容易成功,不容易违反规则,如果插入了红色的结点违反了规则,则就需要通过【修正方法】进行修改,目前是不需要的:
插入75:
插入12,由于插入的结点为红色,但是这就违反了规则3,如果结点是红色的,则其子节点必须是黑色的,所以就需要修正方法来进行修改,将结点的颜色进行翻转,那么此时就变成了:50(红)——左子树25(黑)——右子树75(黑),但这又违反了规则2,根结点是黑色的,所以就需要将红色变成黑色的,结果如下图所示:
插入37:
插入如62、87:
插入6,如果插入红色,又会出现类似之前讲到的问题,所以需要通过规则1,对颜色进行翻转,然后再插入:
插入18:
插入31:
插入13,按理应该插入18的左子树,但是规则4提到,从根结点到每条路径必须包含相同规则的黑色结点,所以此时不满则要求,需要进行修正方法,可以通过2方法,将整棵树拎着 根结点 50 向右旋转:
但是根必须是黑色的,那么就进行一次改变颜色,自行脑补一哈。