[数据结构]红黑树

二叉搜索树
(一)概念
一个二叉搜索树是一个节点有序的二叉树,
(1)根的左分支节点值都小于根节点的值
(2)右分支节点值都大于根节点值
(3)所有子树也都是二叉搜索树

自平衡二叉搜索树
平衡二叉树:一个所有叶子节点的深度差不超过1的二叉搜索树
自平衡二叉搜索树:是指其操作都试图维持平衡的二叉搜索树


红黑树
红黑树是一种自平衡二叉搜索树,红黑树有以下特性:
       1.每个节点不是黑色就是红色的
       2.根节点是黑色的
       3.每个叶节点(NIL)是黑色的
       4.如果一个节点是红色的,那么它的两个子女都是黑色的
       5.从某一个节点到达其子孙叶节点的每一条简单路径上包含相同数量的黑色节点
linux内核中实现的红黑树为rbtree,在rbtree.c文件中,红黑树的优点是所有操作都可以在O(log n)时间内完成,、

linux内核中红黑树的节点用以下结构体表示:

100 struct rb_node
101 {
102         unsigned long  rb_parent_color;
103 #define RB_RED          0
104 #define RB_BLACK        1
105         struct rb_node *rb_right;
106         struct rb_node *rb_left;
107 } __attribute__((aligned(sizeof(long))));

linux的rb_node结构体中隐藏了一个指向其父节点的指针,在rb_parent_color成员中,因为表示红黑只需要一个bit,而指针是以4字节对齐

116 #define rb_parent(r)   ((struct rb_node *)((r)->rb_parent_color & ~3))
117 #define rb_color(r)   ((r)->rb_parent_color & 1)

linux内核通过红黑树找到具体成员是通过容器的形式实现的
#define containner_of(ptr,type,member)

红黑树的根节点以如下的形式表现,这样做的好处是可以不用传递二级指针

#define RB_ROOT (struct rb_root) { NULL, }
110 struct rb_root
111 {
112         struct rb_node *rb_node;
113 };


(二)红黑树的左旋,右旋以及插入操作

关于左旋和右旋具体图解可以参考如下网址点击打开链接

rbtree.c中关于左旋的代码如下所示:

 26 static void __rb_rotate_left(struct rb_node *node, struct rb_root *root)
 27 {
 28         struct rb_node *right = node->rb_right;
 29         struct rb_node *parent = rb_parent(node);
 30 
 31         if ((node->rb_right = right->rb_left))
 32                 rb_set_parent(right->rb_left, node);
 33         right->rb_left = node;
 34 
 35         rb_set_parent(right, parent);
 36 
 37         if (parent)
 38         {
 39                 if (node == parent->rb_left)
 40                         parent->rb_left = right;
 41                 else
 42                         parent->rb_right = right;
 43         }
 44         else
 45                 root->rb_node = right;
 46         rb_set_parent(node, right);
 47 }


 红黑树的插入可以参考以下网址点击打开链接

红黑树详细讲解

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值