红黑树

来源:互联网 发布:最好的短线炒股软件 编辑:程序博客网 时间:2024/06/05 02:49

http://blog.csdn.net/liuben/archive/2009/02/07/3867304.aspx

 

红黑树(Red-Black Tree)是一种二叉查找树(Binary Search Tree),但作了改进,即在每个结点上增加一个存储位表示结点的颜色,可以是RED或BLACK。通过对任何一条从根到叶子的路径上各个结点的着色方式的限制,红黑树确保没有一条路径会比其他路径长出两倍,因而是接近平衡的。

  红黑树的每个节点属性包含五个域:color、key、parent、lchild、rchild。红黑树除了具有二叉搜索树的所有性质之外,还具有以下性质:

  1. 每个结点或是红的,或是黑的。

  2. 根结点是黑的。

  3. 每个叶结点是黑的。

  4. 如果一个结点是红的,则它的两个孩子都是黑的。

  5. 对每个结点,从该结点到其子孙结点的所有路径上包含相同数目的黑结点。

  以上这些规则可以保证整棵树的平衡,红黑树的高度和查找时间都为O(log N)。

  二叉查找树在最坏的情况下可能会变成一个链表(当所有节点按从小到大的顺序依次插入后)。而红黑树在每一次插入或删除节点之后都会花O(log N)的时间来对树的结构作修改,以保证红黑树的性质,从而保持树的平衡。因此,红黑树的查找方法与二叉查找树相同,而Insert和Delete结点的的方法前半部分与二叉查找树相同,而后半部分添加了一些修改树红黑树结构的操作。具体分析请参见“算法导论”一书第13章。下面给出一种红黑树的C实现,修改自Linux内核源码中的红黑树实现(rbtree.h, rbtree.c)。

rbtree.h

 

view plaincopy to clipboardprint?
  1. #ifndef _RBTREE_H   
  2. #define _RBTREE_H   
  3. #include <stdio.h>   
  4. #define RB_RED      0   
  5. #define RB_BLACK    1   
  6. struct rb_key {   
  7.     int key;   
  8. };   
  9. struct rb_node {   
  10.     struct rb_node *rb_parent;   
  11.     struct rb_node *rb_right;   
  12.     struct rb_node *rb_left;   
  13.     struct rb_key rb_key;   
  14.     int rb_color;   
  15. };   
  16. struct rb_root {   
  17.         struct rb_node *rb_node;   
  18. };   
  19. #define rb_parent(r)   ((struct rb_node *)((r)->rb_parent))   
  20. #define rb_color(r)   ((r)->rb_color)   
  21. #define rb_is_red(r)   (!rb_color(r))   
  22. #define rb_is_black(r) rb_color(r)   
  23. #define rb_set_red(r)  do { (r)->rb_color = RB_RED; } while (0)   
  24. #define rb_set_black(r)  do { (r)->rb_color = RB_BLACK; } while (0)   
  25. static inline void rb_set_parent(struct rb_node *rb, struct rb_node *p)   
  26. {   
  27.     rb->rb_parent = p;   
  28. }   
  29. static inline void rb_set_color(struct rb_node *rb, int color)   
  30. {   
  31.         rb->rb_color = color;   
  32. }   
  33. #define RB_ROOT (struct rb_root) { NULL, }   
  34. #define RB_EMPTY_ROOT(root)     ((root)->rb_node == NULL)   
  35. #define RB_EMPTY_NODE(node)     (rb_parent(node) == node)   
  36. #define RB_CLEAR_NODE(node)     (rb_set_parent(node, node))   
  37. extern void rb_insert_color(struct rb_node *, struct rb_root *);   
  38. extern void rb_erase(struct rb_node *, struct rb_root *);   
  39. extern void rb_insert(struct rb_node *, struct rb_root *);   
  40. extern void rb_traverse(struct rb_node *);   
  41. extern struct rb_node *rb_newnode(struct rb_key *);   
  42. extern struct rb_node *rb_search(struct rb_root *, struct rb_key);   
  43. /* Find logical next and previous nodes in a tree */  
  44. extern struct rb_node *rb_next(struct rb_node *);   
  45. extern struct rb_node *rb_prev(struct rb_node *);   
  46. extern struct rb_node *rb_first(struct rb_root *);   
  47. extern struct rb_node *rb_last(struct rb_root *);   
  48. /* Fast replacement of a single node without remove/rebalance/add/rebalance */  
  49. extern void rb_replace_node(struct rb_node *victim, struct rb_node *new_node,   
  50.                             struct rb_root *root);   
  51. static inline void rb_link_node(struct rb_node * node, struct rb_node * parent,   
  52.                                 struct rb_node ** rb_link)   
  53. {   
  54.         node->rb_parent = parent;   
  55.         node->rb_left = node->rb_right = NULL;   
  56.         *rb_link = node;   
  57. }   
  58. #endif  

 

 

rbtree.c

 

view plaincopy to clipboardprint?
  1. #include <stdio.h>   
  2. #include <stdlib.h>   
  3. #include <string.h>   
  4. #include "rbtree.h"   
  5. static void __rb_rotate_left(struct rb_node *node, struct rb_root *root)   
  6. {   
  7.         struct rb_node *right = node->rb_right;   
  8.         struct rb_node *parent = rb_parent(node);   
  9.         if ((node->rb_right = right->rb_left))   
  10.                 rb_set_parent(right->rb_left, node);   
  11.         right->rb_left = node;   
  12.         rb_set_parent(right, parent);   
  13.         if (parent) {   
  14.                 if (node == parent->rb_left)   
  15.                         parent->rb_left = right;   
  16.                 else  
  17.                         parent->rb_right = right;   
  18.         } else  
  19.                 root->rb_node = right;   
  20.         rb_set_parent(node, right);   
  21. }   
  22. static void __rb_rotate_right(struct rb_node *node, struct rb_root *root)   
  23. {   
  24.         struct rb_node *left = node->rb_left;   
  25.         struct rb_node *parent = rb_parent(node);   
  26.         if ((node->rb_left = left->rb_right))   
  27.                 rb_set_parent(left->rb_right, node);   
  28.         left->rb_right = node;   
  29.         rb_set_parent(left, parent);   
  30.         if (parent) {   
  31.                 if (node == parent->rb_right)   
  32.                         parent->rb_right = left;   
  33.                 else  
  34.                         parent->rb_left = left;   
  35.         } else  
  36.                 root->rb_node = left;   
  37.         rb_set_parent(node, left);   
  38. }   
  39. void rb_insert_color(struct rb_node *node, struct rb_root *root)   
  40. {   
  41.     struct rb_node *parent, *gparent;   
  42.     while ((parent = rb_parent(node)) && rb_is_red(parent)) {   
  43.         gparent = rb_parent(parent);   
  44.         if (parent == gparent->rb_left)  { // node is left child of parent   
  45.             {   
  46.                 struct rb_node *uncle = gparent->rb_right;   
  47.                 if (uncle && rb_is_red(uncle)) { // case 1   
  48.                     rb_set_black(uncle);   
  49.                     rb_set_black(parent);   
  50.                     rb_set_red(gparent);   
  51.                     node = gparent;   
  52.                     continue;   
  53.                 }   
  54.             }   
  55.             if (parent->rb_right == node) { // case 2   
  56.                 struct rb_node *tmp;   
  57.                 __rb_rotate_left(parent, root);   
  58.                 tmp = parent;   
  59.                 parent = node;   
  60.                 node = tmp;   
  61.             }   
  62.             // case 3   
  63.             rb_set_black(parent);   
  64.             rb_set_red(gparent);   
  65.             __rb_rotate_right(gparent, root);   
  66.         } else { // node is right child of parent   
  67.             {   
  68.                 struct rb_node *uncle = gparent->rb_left;   
  69.                 if (uncle && rb_is_red(uncle)) { // case 1   
  70.                     rb_set_black(uncle);   
  71.                     rb_set_black(parent);   
  72.                     rb_set_red(gparent);   
  73.                     node = gparent;   
  74.                     continue;   
  75.                 }   
  76.             }   
  77.             if (parent->rb_left == node) { // case 2   
  78.                 struct rb_node *tmp;   
  79.                 __rb_rotate_right(parent, root);   
  80.                 tmp = parent;   
  81.                 parent = node;   
  82.                 node = tmp;   
  83.             }   
  84.             // case 3   
  85.             rb_set_black(parent);   
  86.             rb_set_red(gparent);   
  87.             __rb_rotate_left(gparent, root);   
  88.         }   
  89.     }   
  90.     rb_set_black(root->rb_node);   
  91. }   
  92. static int rb_compare(struct rb_key key1, struct rb_key key2)   
  93. {   
  94.     return (key1.key - key2.key);   
  95. }   
  96. struct rb_node* rb_newnode(struct rb_key *rb_key)   
  97. {   
  98.     struct rb_node *node = (struct rb_node *)malloc(sizeof(struct rb_node));   
  99.     if (node) {   
  100.         node->rb_parent = NULL;   
  101.         node->rb_left = NULL;   
  102.         node->rb_right = NULL;   
  103.         node->rb_color = RB_RED;   
  104.         memcpy(&node->rb_key, rb_key, sizeof(struct rb_key));   
  105.     }   
  106.     return node;   
  107. }   
  108. void rb_insert(struct rb_node *node, struct rb_root *root)   
  109. {   
  110.     struct rb_node *p = root->rb_node;   
  111.     struct rb_node *q = NULL;   
  112.     while (p != NULL) {   
  113.         q = p;   
  114.         if (rb_compare(node->rb_key, p->rb_key) < 0)   
  115.             p = p->rb_left;   
  116.         else  
  117.             p = p->rb_right;   
  118.     }   
  119.     node->rb_parent = q;   
  120.     if (q == NULL) {   
  121.         root->rb_node = node;   
  122.     } else {   
  123.         if (rb_compare(node->rb_key, q->rb_key) < 0)   
  124.             q->rb_left = node;   
  125.         else  
  126.             q->rb_right = node;   
  127.     }   
  128.     rb_insert_color(node, root);   
  129. }   
  130. static void __rb_erase_color(struct rb_node *node, struct rb_node *parent, struct rb_root *root)   
  131. {   
  132.     struct rb_node *other;   
  133.     while ((!node || rb_is_black(node)) && node != root->rb_node)   
  134.     {   
  135.         if (parent->rb_left == node)   
  136.         {   
  137.             other = parent->rb_right;   
  138.             // case 1   
  139.             if (rb_is_red(other))   
  140.             {   
  141.                 rb_set_black(other);   
  142.                 rb_set_red(parent);   
  143.                 __rb_rotate_left(parent, root);   
  144.                 other = parent->rb_right;   
  145.             }   
  146.             // case 2   
  147.             if ((!other->rb_left || rb_is_black(other->rb_left)) &&   
  148.                 (!other->rb_right || rb_is_black(other->rb_right)))   
  149.             {   
  150.                 rb_set_red(other);   
  151.                 node = parent;   
  152.                 parent = rb_parent(node);   
  153.             }   
  154.             else  
  155.             {   
  156.                 // case 3   
  157.                 if (!other->rb_right || rb_is_black(other->rb_right))   
  158.                 {   
  159.                     struct rb_node *o_left;   
  160.                     if ((o_left = other->rb_left))   
  161.                         rb_set_black(o_left);   
  162.                     rb_set_red(other);   
  163.                     __rb_rotate_right(other, root);   
  164.                     other = parent->rb_right;   
  165.                 }   
  166.                 // case 4   
  167.                 rb_set_color(other, rb_color(parent));   
  168.                 rb_set_black(parent);   
  169.                 if (other->rb_right)   
  170.                     rb_set_black(other->rb_right);   
  171.                 __rb_rotate_left(parent, root);   
  172.                 node = root->rb_node;   
  173.                 break;   
  174.             }   
  175.         }   
  176.         else  
  177.         {   
  178.             other = parent->rb_left;   
  179.             // case 1   
  180.             if (rb_is_red(other))   
  181.             {   
  182.                 rb_set_black(other);   
  183.                 rb_set_red(parent);   
  184.                 __rb_rotate_right(parent, root);   
  185.                 other = parent->rb_left;   
  186.             }   
  187.             // case 2   
  188.             if ((!other->rb_left || rb_is_black(other->rb_left)) &&   
  189.                 (!other->rb_right || rb_is_black(other->rb_right)))   
  190.             {   
  191.                 rb_set_red(other);   
  192.                 node = parent;   
  193.                 parent = rb_parent(node);   
  194.             }   
  195.             else  
  196.             {   
  197.                 // case 3   
  198.                 if (!other->rb_left || rb_is_black(other->rb_left))   
  199.                 {   
  200.                     register struct rb_node *o_right;   
  201.                     if ((o_right = other->rb_right))   
  202.                         rb_set_black(o_right);   
  203.                     rb_set_red(other);   
  204.                     __rb_rotate_left(other, root);   
  205.                     other = parent->rb_left;   
  206.                 }   
  207.                 // case 4   
  208.                 rb_set_color(other, rb_color(parent));   
  209.                 rb_set_black(parent);   
  210.                 if (other->rb_left)   
  211.                     rb_set_black(other->rb_left);   
  212.                 __rb_rotate_right(parent, root);   
  213.                 node = root->rb_node;   
  214.                 break;   
  215.             }   
  216.         }   
  217.     }   
  218.     if (node)   
  219.         rb_set_black(node);   
  220. }   
  221. void rb_erase(struct rb_node *node, struct rb_root *root)   
  222. {   
  223.     struct rb_node *child, *parent;   
  224.     int color;   
  225.     if (!node->rb_left)   
  226.         child = node->rb_right;   
  227.     else if (!node->rb_right)   
  228.         child = node->rb_left;   
  229.     else  
  230.     {   
  231.         struct rb_node *old = node, *left;   
  232.         node = node->rb_right;   
  233.         while ((left = node->rb_left) != NULL)   
  234.             node = left;   
  235.         child = node->rb_right;   
  236.         parent = rb_parent(node);   
  237.         color = rb_color(node);   
  238.         if (child)   
  239.             rb_set_parent(child, parent);   
  240.         if (parent == old) {   
  241.             parent->rb_right = child;   
  242.             parent = node;   
  243.         } else  
  244.             parent->rb_left = child;   
  245.         node->rb_color = old->rb_color;   
  246.         node->rb_parent = old->rb_parent;   
  247.         node->rb_right = old->rb_right;   
  248.         node->rb_left = old->rb_left;   
  249.         if (rb_parent(old))   
  250.         {   
  251.             if (rb_parent(old)->rb_left == old)   
  252.                 rb_parent(old)->rb_left = node;   
  253.             else  
  254.                 rb_parent(old)->rb_right = node;   
  255.         } else  
  256.             root->rb_node = node;   
  257.         rb_set_parent(old->rb_left, node);   
  258.         if (old->rb_right)   
  259.             rb_set_parent(old->rb_right, node);   
  260.         goto color;   
  261.     }   
  262.     parent = rb_parent(node);   
  263.     color = rb_color(node);   
  264.     if (child)   
  265.         rb_set_parent(child, parent);   
  266.     if (parent)   
  267.     {   
  268.         if (parent->rb_left == node)   
  269.             parent->rb_left = child;   
  270.         else  
  271.             parent->rb_right = child;   
  272.     }   
  273.     else  
  274.         root->rb_node = child;   
  275.  color:   
  276.     if (color == RB_BLACK)   
  277.         __rb_erase_color(child, parent, root);   
  278. }   
  279. struct rb_node *rb_first(struct rb_root *root)   
  280. {   
  281.     struct rb_node  *n;   
  282.     n = root->rb_node;   
  283.     if (!n)   
  284.         return NULL;   
  285.     while (n->rb_left)   
  286.         n = n->rb_left;   
  287.     return n;   
  288. }   
  289. struct rb_node *rb_last(struct rb_root *root)   
  290. {   
  291.     struct rb_node  *n;   
  292.     n = root->rb_node;   
  293.     if (!n)   
  294.         return NULL;   
  295.     while (n->rb_right)   
  296.         n = n->rb_right;   
  297.     return n;   
  298. }   
  299. struct rb_node *rb_next(struct rb_node *node)   
  300. {   
  301.     struct rb_node *parent;   
  302.     if (rb_parent(node) == node)   
  303.         return NULL;   
  304.     /* If we have a right-hand child, go down and then left as far  
  305.        as we can. */  
  306.     if (node->rb_right) {   
  307.         node = node->rb_right;    
  308.         while (node->rb_left)   
  309.             node=node->rb_left;   
  310.         return node;   
  311.     }   
  312.     /* No right-hand children.  Everything down and left is  
  313.        smaller than us, so any 'next' node must be in the general  
  314.        direction of our parent. Go up the tree; any time the  
  315.        ancestor is a right-hand child of its parent, keep going  
  316.        up. First time it's a left-hand child of its parent, said  
  317.        parent is our 'next' node. */  
  318.     while ((parent = rb_parent(node)) && node == parent->rb_right)   
  319.         node = parent;   
  320.     return parent;   
  321. }   
  322. struct rb_node *rb_prev(struct rb_node *node)   
  323. {   
  324.     struct rb_node *parent;   
  325.     if (rb_parent(node) == node)   
  326.         return NULL;   
  327.     /* If we have a left-hand child, go down and then right as far  
  328.        as we can. */  
  329.     if (node->rb_left) {   
  330.         node = node->rb_left;    
  331.         while (node->rb_right)   
  332.             node=node->rb_right;   
  333.         return node;   
  334.     }   
  335.     /* No left-hand children. Go up till we find an ancestor which  
  336.        is a right-hand child of its parent */  
  337.     while ((parent = rb_parent(node)) && node == parent->rb_left)   
  338.         node = parent;   
  339.     return parent;   
  340. }   
  341. void rb_replace_node(struct rb_node *victim, struct rb_node *new_node, struct rb_root *root)   
  342. {   
  343.     struct rb_node *parent = rb_parent(victim);   
  344.     /* Set the surrounding nodes to point to the replacement */  
  345.     if (parent) {   
  346.         if (victim == parent->rb_left)   
  347.             parent->rb_left = new_node;   
  348.         else  
  349.             parent->rb_right = new_node;   
  350.     } else {   
  351.         root->rb_node = new_node;   
  352.     }   
  353.     if (victim->rb_left)   
  354.         rb_set_parent(victim->rb_left, new_node);   
  355.     if (victim->rb_right)   
  356.         rb_set_parent(victim->rb_right, new_node);   
  357.     /* Copy the pointers/colour from the victim to the replacement */  
  358.     *new_node = *victim;   
  359. }   
  360. struct rb_node *rb_search(struct rb_root *root, struct rb_key key)   
  361. {   
  362.     struct rb_node *p = root->rb_node;   
  363.     while(p != NULL && rb_compare(p->rb_key, key) != 0) {   
  364.         p = (rb_compare(p->rb_key, key) > 0) ? p->rb_left : p->rb_right;   
  365.     }   
  366.     return p;   
  367. }   
  368. void rb_traverse(struct rb_node *p)   
  369. {   
  370.     if (p) {   
  371.         if (p->rb_left)   
  372.             rb_traverse(p->rb_left);   
  373.         printf(" %d ", p->rb_key.key);   
  374.         if (p->rb_right)   
  375.             rb_traverse(p->rb_right);   
  376.     }   
  377. }  

 

 

demo.c

 

view plaincopy to clipboardprint?
  1. #include <stdio.h>  
  2. #include <stdlib.h>  
  3. #include "rbtree.h"   
  4. int main(int argc, char *argv[])   
  5. {   
  6.     int i;   
  7.     struct rb_root root;   
  8.     root.rb_node = NULL;   
  9.     for (i = 2; i < argc; i++ ) {   
  10.         struct rb_key rb_key;   
  11.         rb_key.key = atol(argv[i]);   
  12.         struct rb_node *node = rb_newnode(&rb_key);   
  13.         if (node) {   
  14.             rb_insert(node, &root);   
  15.         }   
  16.     }   
  17.     rb_traverse(root.rb_node);   
  18.     printf("/n");   
  19.     struct rb_key rb_key;   
  20.     rb_key.key = atol(argv[1]);   
  21.     struct rb_node *node = rb_search(&root, rb_key);   
  22.     if (node) {   
  23.         printf("key = %d/n", node->rb_key.key);   
  24.         rb_erase(node, &root);   
  25.         rb_traverse(root.rb_node);   
  26.         printf("/n");   
  27.     } else {   
  28.         printf("%d is not found/n", rb_key.key);   
  29.     }   
  30.     return 0;   
  31. }  
原创粉丝点击