由set到红黑树

来源:互联网 发布:文泰刻绘怎么设置端口 编辑:程序博客网 时间:2024/05/16 14:49

    本文算是上一篇STL set学习的后续。主要是review代码的时候,接着对set进行了讨论,需要明白set到底是如何进行insert和find的。因此,简单地研究了一下stl代码,set是基于RB-tree(红黑树)实现的。上网查了相关的资料,都写得不好,包括那些所谓“真正让你了解红黑树”的文章,都不如直接读源代码理解来得快,有《STL源码剖析》的帮助,比网上任何资料都更加明白。也真正明白上一篇set中第3点所说的排序规则,在RB-tree中是如何实现的了。简单做了些笔记,post上来。

1. 平衡二叉搜索树 (balance binary search tree)

2. AVL树:Adelson-Velskii-Landis tree又是以人名命名的——就是原来学的平衡二叉树

    这是一个弱二叉平衡树,即左右子树的高度相差最多为1,用以保证“对数深度” O(logN)的平衡状态

    左左,右右的单旋转

    左右,右左的双旋转

3. RB-tree: 红黑树,是AVL的一种,被广泛使用

    是SGI STL唯一实现的一种搜索树,作为关联式容器(associated contrainers)的底部机制

    必须满足以下规则:
                
    也就是说,要插入一个节点,首先得根据二叉搜索树的规则,找到插入点(从root节点开始,左小右大的规则)

    找到之后再根据RB-tree的规则,进行颜色的调整,以及位置旋转,旋转过后可能还需要改变颜色。

4. 对于set容器,底层实现是由RB-tree实现的,是调用了stl_tree.h里RB-tree的insert, delete, find的操作

    调用insert_unique(), insert的规则如下:(即实现代码,来自STL源码剖析-侯捷)

    

     解释:x为当前树中的节点,v为即将插入的新节点,离开while时,y为插入点的父节点

              此时,已调用一次operator<()来比较v和y的大小
  
              1)如果上一次v < y,若,y是最左节点,则v插入到y的左侧,insert(v) to y

                                              若,y不是最左节点,则回到y的上一节点,走2)

              2)如果上一次v >= y, 或者v<y但y不是最左节点,则走2)
  
                   再次调用operator<()来比较y和v的大小,如果y < v, 说明v将插入到y的右侧

                                                                             如果 y >= v,则说明y == v,即键值重复

5. find()操作

    注意,也是进行两次比较,x为树中节点,k为新节点,第一次比较x < k?

                                                                                 第二次比较k < x?
    
     

原创粉丝点击