红黑树c源码实现与剖析
作者:July 、那谁 时间:二零一一年一月三日
-------------------------
前言:
红黑树作为一种经典而高级的数据结构,相信,已经被不少人实现过,但不是因为程序不够完善而无法运行,就是因为程序完全没有注释,初学者根本就看不懂。
此份红黑树的c源码最初从linux-lib-rbtree.c而来,后经一网友那谁用c写了出来。在此,向原作者表示敬意。但原来的程序存在诸多问题,且全程序没有任何一行注释。没有一行注释的程序,令程序的价值大打折扣。所以,我特把这份源码放到了windows xp+vc 6.0上,一行一行的完善修正,一行一行的给它添加注释,至此,红黑树c带完美注释的源码,就摆在了您眼前,有不妥、不正之处,还望不吝指正。
------------ok,咱们开始吧。
相信,经过我前俩篇博文对红黑树的介绍,你应该对红黑树有了透彻的理解了(没看过的朋友,可事先查上面的倆篇文章,或与此文的源码剖析对应着看)。
本套源码剖析把重点放在红黑树的3种插入情况,与红黑树的4种删除情况。其余的能从略则尽量简略。
目录:
一、左旋代码分析
二、右旋
三、红黑树查找结点
四、红黑树的插入
五、红黑树的3种插入情况
六、红黑树的删除
七、红黑树的4种删除情况
八、测试用例
好的,咱们还是先从树的左旋、右旋代码,开始(大部分分析,直接给注释):
view plaincopy to clipboardprint?
//一、左旋代码分析
/*-----------------------------------------------------------
| node right
| / ==> /
| a right node y
| / /
| b y a b //左旋
-----------------------------------------------------------*/
static rb_node_t* rb_rotate_left(rb_node_t* node, rb_node_t* root)
{
rb_node_t* right = node->right; //指定指针指向 right<--node->right
if ((node->right = right->left))
{
right->left->parent = node; //好比上面的注释图,node成为b的父母
}
right->left = node; //node成为right的左孩子
if ((right->parent = node->parent))
{
if (node == node->parent->right)
{
node->parent->right = right;
}
else
{
node->parent->left = right;
}
}
else
{
root = right;
}
node->parent = right; //right成为node的父母
return root;
}
//二、右旋
/*-----------------------------------------------------------
| node left
| / /
| left y ==> a node
| / /
| a b b y //右旋与左旋差不多,分析略过
-----------------------------------------------------------*/
static rb_node_t* rb_rotate_right(rb_node_t* node, rb_node_t* root)
{
rb_node_t* left = node->left;
if ((node->left = left->right))
{
left->right->parent = node;
}
left->right = node;
if ((left->parent = node->parent))
{
if (node == node->parent->right)
{
node->parent->right = left;
}
else
{
node->parent->left = left;
}
}
else
{
root = left;
}
node->parent = left;
return root;
}
//三、红黑树查找结点
//----------------------------------------------------
//rb_search_auxiliary:查找
//rb_node_t* rb_search:返回找到的结点
//----------------------------------------------------
static rb_node_t* rb_search_auxiliary(key_t key, rb_node_t* root, rb_node_t** save)
{
rb_node_t *node = root, *parent = NULL;
int ret;
while (node)
{
parent = node;
ret = node->key - key;
if (0 < ret)
{
 
补充:软件开发 , C语言 ,