1 B树
B树(B-树)是一种平衡的多路搜索树,多用于文件系统、数据库的实现。
1.1 B树的特点
- 1 个节点可以存储超过 2 个元素、可以拥有超过 2 个子节点
- 拥有二叉搜索树的一些性质
- 平衡,每个节点的所有子树高度一致
- 比较矮
1.2 m阶B树
m阶B树中的m指一棵B树中存在的最大子节点数,如下图中的就是一棵3阶B树,也可以称为2-3树(2-3是非根节点可以有的子节点数,见下性质)
1.2.1 m阶B树的性质
假设B树一个节点可以存储元素的个数为:x,则:
- 根节点中:1<=x<m-1
- 非根节点中:ceiling(x/2)-1<=x<=m-1 ,ceiling表示向上取整
那么在假设B树中一个节点可以拥有的子节点树为y,则:
- 根节点中:2<=y<=m
- 非根节点中:ceiling(x/2)<=y<=m
所以当m=3,y也就是非根节点拥有的子节点个数范围为[2,3],所以也将m阶B树称为2-3树。同理,那么5阶B树可以叫3-4-5树或(3,5)树。
1.3 B树的搜索
B树的搜索跟二叉搜索树的搜索类似。
- 先在节点内部从小到大开始搜索元素
- 如果找到了元素,则搜索结束
- 如果没找到,再去对应的子节点中搜索元素,重复1
1.4 B树的添加
在B树中,新添加元素的元素一定是添加到叶子节点。如下图。
1.4.1添加产生的上溢
但也有可能因为添加节点,导致某个节点的元素树超过了m-1的限制,我们称之为上溢,如下图中的4阶B树。
此时的处理方法是,让上溢节点的中间元素与父节点合并,然后将原上溢节点由中间节点分为两个,如下所示。
当然这个操作让父节点增加了一个元素,可能导致父节点上溢,不过如果父节点上溢,我们还是采用同样的操作。
经过多次操作,我们就可以将B树恢复正常了。
1.5 B树的删除
B树的删除逻辑与BST二叉搜索树几乎完全相同。
如果删除的节点是叶子节点,那么直接删除就好,如下。
如果是非叶子节点,那么找到该节点的前驱或后继节点,用其元素值覆盖,然后删除前驱或者后继节点。
1.5.1 删除产生的下溢
由于非根节点的元素数范围是:ceiling(m/2)-1<=x<m-1,当节点中元素数过少也会不符合B树定义。
下溢处理的两种情况如下所示:
(1)下溢节点的兄弟节点有多余下限个元素,则我们可以从兄弟节点那里借一个元素来补偿。具体如下所示。
可以看出这个操作和AVL树的左旋右旋非常得相似。
(2)如果兄弟节点也没有多余的元素,那么我们选择将父节点的元素 挪下来跟左右子节点进行合并(可以推算,合并产生的节点数不可能上溢,因当前情况下,需要合并的两个子节点元素个数一定为floor(m/2)-1,内那么合并后的节点数为2floor(m/2)-2+1-1=2floor(m/2)-2,而向上取整最多比不取整多1,所以结果最大为2*m/2-2+2=m。这样可能导致父节点也产生下溢,但我们可以用同样的逻辑对父节点继续处理,直到不再出现下溢为止。如下面这棵5阶B树,节点元素数:2<=x<=4。