2.3 删除像二叉查找树的删除操作一样,首先需要找到所需删除的结点,然后根据该结点左右子树的有无分为三种情形:
文章插图
若node结点的颜色属性为黑色,则需要调用__rb_erase_color函数来进行调整 。
void rb_erase(struct rb_node *node, struct rb_root *root){ struct rb_node *child, *parent; int color; if (!node->rb_left) //删除结点无左子树 child = node->rb_right; else if (!node->rb_right) //删除结点无右子树 child = node->rb_left; else //左右子树都有 { struct rb_node *old = node, *left; node = node->rb_right; while ((left = node->rb_left) != NULL) node = left; if (rb_parent(old)) { if (rb_parent(old)->rb_left == old) rb_parent(old)->rb_left = node; else rb_parent(old)->rb_right = node; } else root->rb_node = node; child = node->rb_right; parent = rb_parent(node); color = rb_color(node); if (parent == old) { parent = node; } else { if (child) rb_set_parent(child, parent); parent->rb_left = child; node->rb_right = old->rb_right; rb_set_parent(old->rb_right, node); } node->rb_parent_color = old->rb_parent_color; node->rb_left = old->rb_left; rb_set_parent(old->rb_left, node); goto color; } //end else parent = rb_parent(node); //获得删除结点的双亲结点 color = rb_color(node); //获取删除结点的颜色属性 if (child) rb_set_parent(child, parent); if (parent) { if (parent->rb_left == node) parent->rb_left = child; else parent->rb_right = child; } else root->rb_node = child; color: if (color == RB_BLACK) //如果删除结点的颜色属性为黑色,则需调用__rb_erase_color函数来进行调整 __rb_erase_color(child, parent, root);}
2.4 遍历rb_first和rb_next函数可组成中序遍历,即以升序遍历红黑树中的所有结点 。struct rb_node *rb_first(const struct rb_root *root){ struct rb_node *n; n = root->rb_node; if (!n) return NULL; while (n->rb_left) n = n->rb_left; return n;} struct rb_node *rb_next(const struct rb_node *node){ struct rb_node *parent; if (rb_parent(node) == node) return NULL; /* If we have a right-hand child, go down and then left as far as we can. */ if (node->rb_right) { node = node->rb_right; while (node->rb_left) node=node->rb_left; return (struct rb_node *)node; } /* No right-hand children. Everything down and left is smaller than us, so any 'next' node must be in the general direction of our parent. Go up the tree; any time the ancestor is a right-hand child of its parent, keep going up. First time it's a left-hand child of its parent, said parent is our 'next' node. */ while ((parent = rb_parent(node)) && node == parent->rb_right) node = parent; return parent;}
推荐阅读
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- 石楠树为什么有精子味,石楠花为什么污
- 桐树花的功效与作用泡,泡桐树有什么作用
- 云南白茶的功效,云南古树白茶的特点
- 椿树图片,香椿是什么样子图片
- 紫沙茶罐图片及价格,广西大红花油茶树挂果图片及视频大果红花油茶图片大全欣赏
- 石竹草图片,明月草(又名降糖草降糖树血米草简介及图片
- 红玉兰树,红玉兰树适合什么土壤生长
- 陈皮泡红茶好还是绿茶好,常喝红茶好还是绿茶好
- 类似忍冬,原神忍冬之树有什么作用
- 泡桐树花有什么作用,泡桐树有什么作用