红黑树的定义
红黑树是一颗自平衡二叉查找树,但并不是一颗平衡二叉树(叶子结点所处的层级差不会超过1),这里的平衡是一种相对平衡。 红黑树需要满足以下五个条件
- 红黑树的节点具有颜色,要么是黑色要么是红色
- 叶子结点(nil)的颜色都是黑色的
- 所有红色结点的子节点都是黑色的
- 从根节点到所有叶子结点的路径上经过的黑结点数量都是相同的(黑高度)
- 根节点是黑色的 正因是满足上述五个条件,红黑树才能保持相对平衡
红黑树的自平衡
红黑树结点的插入与删除等操作都可能会破坏树的平衡(上文的五个条件),为了满足条件,需要进行左旋、右旋、着色操作维持树的相对平衡。
红黑树是一颗二叉查找树,因此具有左小右大的特点,左 < 根 < 右的特点
左旋
下图进行左旋 x结点的右结点取代x占据x所处的位置,因x小于y因此x成为y的左孩子,而y原本的左孩子b因为原来是x的右子树成员,因此成为x的右孩子。
右旋
下图进行右旋 x结点的左结点取代x占据x所处的位置,因x大于y所以x成为y的右孩子,而y原来的右孩子c因为原来是x的左子树成员呢,因此成为x的左孩子
着色
插入结点是红色的,因为插入结点必将替换原来的一个叶子结点,红结点的子节点一定是黑色的,替换掉一个黑色叶子结点后,红色结点的子节点能使得原本经过该节点的路径又重新拥有一个黑色节点,满足黑高度保持不变,但是可能会条件3
若插入结点的父结点是黑节点,则无需做任何调整即可满足五个条件
若插入结点的父结点是红结点,则需要区分场景
若叔叔结点是黑色的,则将该结点左旋或右旋至祖父结点后,变为黑色,其子节点设置为红色
若叔叔结点是红色的则直接修改父结点和叔叔结点为黑色,因为以祖父结点为子树的根来看当前子树的黑高增加了1,因此将祖父结点的颜色设置为红色(原来必定为黑色因为父结点和叔叔结点都是红色),若曾祖父结点还是红色的(即祖父和曾祖父都是红色的依然不满足条件)则重复上述步骤