第三部分 数据结构
第13章 红黑树
1. 红黑树的性质
- 每个节点或是红色的,或是黑色的
- 根结点是黑色的
- 每个叶结点(NIL)是黑色的
- 如果一个叶结点是红色的,则它的两个子结点都是黑色的
- 对每个结点,从该结点到其它所有后代叶结点的简单路径上,均包含相同数目的黑色结点
黑高:从某个结点x出发(不含该节点)到达一个叶结点的任意一条简单路径上的黑色结点个数称为该结点的黑高。
2. 旋转
- 左旋,以x到y的链为“支轴”进行。它使y成为该子树新的根节点,x成为y的左孩子,y的左孩子成为x的右孩子
- 右旋
Left-Rotate(T, x)
y = x.right // set y
// turn y's left subtree into x's right subtree
x.right = y.left
if y.left != T.nil
y.left.p = x
y.p = x.p // link x's parent to y
if x.p = T.nil
T.root = y
else if x = x.p.left
x.p.left = y
else
x.p.right = y
y.left = x // put x on y's left
x.p = y
3. 插入[参考]
RB-Insert(T, z)
y = T.nil
x = T.root
while x != T.nil
y = x
if z.key < x.key
x = x.left
else
x = x.right
z.p = x
if y == T.nil
T.root = z
else if z.key < y.key
y.left = z
else
y.right = z
z.left = T.nil
z.right = T.nil
z.color = RED
RB-Insert-Fixup(T, z)
RB-Insert-Fixup(T, z)
while z.p.color == RED
if z.p == z.p.p.left
y = z.p.p.right
if y.color == RED
z.p.color = BLACK // case 1
y.color = BLACK // case 1
z.p.p.color = RED // case 1
z = z.p.p // case 1
else if z == z.p.right
z = z.p // case 2
Left-Rotate(T, z) // case 2
z.p.color = BLACK // case 3
z.p.p.color = RED // case 3
Right-Rotate(T, z.p.p) // case 3
else
(same as then clause
with "right" and "left" exchanged)
T.root.color = BLACK
4. 删除[参考]
RB-Delete(T, z)
y = z
y-original-color = y.color
if z.left == T.nil
x = z.right
RB-Transplant(T, z, z.right)
else z.right == T.nil
x = z.left
RB-Transplant(T, z, z.left)
else
y = Tree-Mininum(z.right)
y-original-color = y.color
x = y.right
if y.p == z
x.p = y
else
RB-Transplant(T, y, y.right)
y.right = z.right
y.right.p = y
RB-Transplant(T, z, y)
y.left = z.left
y.left.p = y
y.color = z.color
if y-original-color == BLACK
RB-Delete-Fixup(T, x)
RB-Delete-Fixup(T, x)
while x != T.nil and x.color == BLACK
if x == x.p.left
w = x.p.right
if w.color == RED
w.color = BLACK // case 1
x.p.color = RED // case 1
Left-Rotate(T, x.p) // case 1
w = x.p.right // case 1
if w.left.color == BLACK and w.right.color == BLACK
w.color = RED // case 2
x = x.p // case 2
else if w.right.color == BLACK
w.left.color = BLACK // case 3
w.color = RED // case 3
Right-Rotate(T, w) // case 3
w = x.p.right // case 3
w.color = x.p.color // case 4
x.p.color = BLACK // case 4
w.right.color = BLACK // case 4
Left-Rotate(T, x.p) // case 4
x = T.root // case 4
else
(same as then clause with "right" and "left" exchanged)
x.color = BLACK