B树与B+树简单了解


关于B树和B+树

小灰算法

漫画:什么是B-树?

漫画:什么是B+树?

B-树
为什么要使用B-树

二叉查找树速度和比较次数都是最小的,但是需要考虑磁盘IO问题

数据库索引是存在磁盘上的,加载的时候不可能整个索引都加载到内存,只能逐一加载每一个磁盘页(每一个磁盘页对应一个索引树节点)。

首先假设一颗二叉查找树:

二叉查找树

查找次数最大为树的高度,也就是要进行4次磁盘IO。

将“瘦高”的树变得“矮胖”

B树(就是B-树)主要目的是为了解决磁盘IO次数的。其中每个节点包括k个孩子,k取决于磁盘页大小。

k最大值就是k阶B树(下面这个应该是3阶B树)

举例一个B树

其改善的地方,就是每个节点都是一个磁盘页,每次加载会将这一整个节点加载到内存中。在内存中比较的速度比磁盘IO快多了。

B-树插入

B-树一大优势:自平衡

插入过程比较麻烦,涉及到节点分裂。

插入4

节点3,5已经是两元素节点,无法再增加。父亲节点 2, 6 也是两元素节点,也无法再增加。根节点9是单元素节点,可以升级为两元素节点。于是拆分节点3,5与节点2,6,让根节点9升级为两元素节点4,9。节点6独立为根节点的第二个孩子。

节点分裂平衡

B-树删除

删除11

删除11后,节点12只有一个孩子,不符合B树规范。因此找出12,13,15三个节点的中位数13,取代节点12,而节点12自身下移成为第一个孩子。(这个过程称为左旋

B-树左旋

B+树

B+树举例

性质1:父节点中的元素,出现在了子节点中,而且是其中最大的;

重复元素

性质2:因为包括父节点元素,所以说叶子节点中,包括所有元素。而且连在一起成了个链表

叶子节点

卫星数据:卫星其实就是索引,一个指针,指向实际地址。下面图里的Data就是卫星数据。

B-树中的卫星数据

B+树中的卫星数据

在数据库的聚集索引(Clustered Index)中,叶子节点直接包含数据。MySQL中的InnoDB引擎。

非聚集索引(NonClustered Index)中,叶子节点带有指向数据的指针。MySQL中MyISAM引擎。

与B-树对比

其查询:

B+树中间节点没有存储卫星数据(全在叶子节点上),所以说可以存储更多索引。IO次数更少

B+树必须查询到叶子节点,而B-树不一定。

B+树查询稳定,B-树则不是。

范围查询

查询分为单元素查询,和范围查询。

单元素查询比较容易理解;

而范围查询是指查询一个范围,比如“3到11”之间的所有数字。

B-树必须要去树的中序遍历

而B+树在找到3之后,根据叶子节点的链表可以直接查询到。

叶子节点链表遍历

总结

B树:
  • 为了解决磁盘IO问题,使用B树。一个节点就是一个磁盘页。
  • B树插入与删除比较麻烦,需要节点分裂与自旋,重要特性自平衡。
  • MongoDB和文件系统使用B-树。
B+树:
  • B+树只在叶子节点中存入数据,而非叶子节点中存的只是索引。
    • 所以说B+树一定要查到叶子节点,稳定查询。而B树则不是。
    • 所以说一个非叶子节点存的比B树的更多,更能解决磁盘IO问题。
  • B+树子节点中包括父节点的数据,所以说叶子节点包括所有数据。
  • 而且叶子节点之间用指针相连,形成了一个链表。做范围查询非常简单。
数据库索引

MySQL中B+树索引与哈希索引。

B+树索引:

  • 非聚簇索引:MySQL的MyISAM引擎,B+树节点里面存储的是索引与数据地址。
  • 聚簇索引:MySQL的InnoDB引擎
    • 主索引:非叶子节点存储主键,叶子节点存储数据;
    • 辅助索引:节点中存主键,然后再根据主索引去找。

哈希索引:

  • MyISAM不支持
  • InnoDB会自动在使用频繁的数据上添加,自动在B+树索引的基础上创建一个哈希索引。

文章作者: SongX64
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 SongX64 !
  目录