树的探索之旅
学习心得
- 不同的树有着不同的功能,核心的功能就是快速查询
- 而我们要学习的是树的结构和结构带来的便捷查询逻辑
- 所谓调整平衡的算法只是为了保证树形符合自身规定的性质/特征(本质上没有固定的调整算法)
二叉树(树的基础形态)
更详尽的描述参考:https://baike.baidu.com/item/%E4%BA%8C%E5%8F%89%E6%A0%91/1602879?fr=aladdin
其他参考文档:http://data.biancheng.net/view/192.html
术语
- 结点:包含一个数据元素及若干指向子树分支的信息
- 结点的度:一个结点拥有子树的数目称为结点的度
- 叶子结点:也称为终端结点,没有子树的结点或者度为零的结点
- 分支结点:也称为非终端结点,度不为零的结点称为非终端结点
- 深度:也称为树的高度,树中最大层数
- 度:子分支数
性质
-
第 i 层最多有 2 i − 1 2^{i-1} 2i−1 个结点
如:第5层最多16个( 2 4 2^{4} 24)
-
共 i 层,最多结点数为 2 i − 1 2^i-1 2i−1 个结点
如:共5层最多31个( 2 5 − 1 2^5-1 25−1)
-
叶子结点数(i)永远比度为2的分支结点数(j)多一个
如:18个叶子结点就会有17个度为2分支结点
满二叉树
完全二叉树
平衡二叉树(AVL)
所谓不平衡:左子树与右子树的深度差最大为1
之所以需要平衡
普通二叉树在某种排列下会导致形成连表结构,从而失去了树的意义(如图)。
平衡调整算法
左旋
右旋
左右旋
- 适用于左子结点右边深度比左边大(如图)
右左旋
- 适用于右子结点左边深度比右边大(如图)
红黑树
个人理解
基于平衡树,红黑树相对于平衡树的平衡程度更严格,也就是平衡调整的复杂度提高了,但是确保了查询的效率,适合数据量大
术语
- NIL:空的叶子结点
特性
- 根结点是黑色
- 每个叶子结点都是黑色的空结点(NIL节点)
- 红色结点的子结点是黑色的(因特性5的约束,该特性可以理解为红黑交替)
- 新插入的结点是红色的
- 每条通往叶子结点(NIL)的路径所包含的黑色结点数一样
调整算法
换色
- 补充一下: 7 是新插入的结点
旋转(和平衡树一样)
B树(B-树)
术语
- 阶:决定结点最大度数,同时也限制结点中值的个数(最少3阶)
性质
- 一个结点可存储多个值(指定的阶数之内)
- 阶的取值大小取决于磁盘页大小
- 结点里的值从小到大排序
- 所有叶结点深度相同,就是树的高度
- 分支结点的度数是自身值个数+1
- 分支节点至少存在容量一半以上个值(容量为奇数时向下取整)
插入流程(结点分裂)
删除流程(兄弟补位、结点合并)
兄弟补位
结点合并(无法补位的情况下使用)
B+树
李大爷遇到的疑惑(两个B+树?)
李大爷不是科班出身,之前并没有在书上看到过树结构的数据类型,所以这篇文档全靠百度。
而百度却给出了两个B+树结构,还都有相关文档和说明,顿然有股平行时空的科幻感(开始怀疑人生)。
揭晓答案:因为 mysql 的B+树实现是经过特殊改造的,因此就出现了【mysql 定制版】和【B树升级版】(名字时李大爷起的,答案是某线上学习机构老师的解释)
mysql 定制版
性质
在B树的基础上有如下调整:
- 叶子结点才存储数据,其他节点都是索引(叶子结点包含了其他节点的值)
- 与B树不同,结点中值的数量等于度的数量
- 每个叶子结点之间都有一个指针指向右边的叶子结点
- 叶子结点外所有结点只记录子结点的最小值(有的是最大值)作为索引
插入流程(编的,希望有看过源码的大佬可以指正一下)
删除流程(等知道正确答案了再补上)
B树升级版
性质
在B树的基础上有如下调整:
- 叶子结点才存储数据,其他节点都是索引(叶子结点包含了其他节点的值)
- 每个叶子结点之间都有一个指针指向右边的叶子结点