-
静态/动态:静态查找表仅查找,动态可能会有插入元素等操作
-
平均查找长度(ASL):平均比较次数
静态查找表
1. 顺序表
逐个遍历
2. 有序表
-
二分查找
-
斐波那契查找
如果表长 m = F n + 1 − 1 m=F_{n+1}-1 m=Fn+1−1
则可以把表分为两段加一点:
长为 F n − 1 F_n-1 Fn−1的一段、 a r r [ F n ] arr[F_n] arr[Fn]、长为 F n − 1 − 1 F_{n-1}-1 Fn−1−1的一段
这样获得一个固定比例的索引来查找,索引只用加减法这方面比二分查找的乘除运算快
-
插值查找
3. 索引顺序表
有两部分:
-
分块有序的顺序表
-
记录顺序表块中最大项的有序表,即索引表
查找过程:先在索引表中找到对应块,再去块中遍历。
动态查找表
1. 二叉排序树
在插入新节点产生失衡后,进行平衡化旋转。
有两个问题需要解决:
-
如何在插入新节点后更新bf
-
失衡后如何进行平衡化旋转
更新平衡因子
平衡化旋转
插入新节点后,距新节点最近的失衡节点就记为a,根据新节点在a子树的位置,分为四种情况。
根据上述假设产生的制约因素,每种情况插入前各部分的深度/bf是确定的。
而平衡旋转的过程,无非就是两件事:
-
确定旋转后的形状
-
确定旋转后的度数
LL
插入前:a.bf = 1, bL = bR = aR
旋转后:a.bf = b.bf = 0
LR
插入前:
-
a.bf = 1, b.bf = 0, c.bf = 0
-
cL = cR, bL = aR
-
cL + 1 = bL
旋转后:
-
c.bf = 0
-
a.bf, b.bf = (0, 1) or (-1, 0)
RR
同LL
RL
同RL
2. B-树、B+树
m阶B-树
1. 定义
重点:
-
每个节点的结构:
( n , A 0 , K 1 , A 1 , . . . , A n , K n ) (n,A_0,K_1,A_1,...,A_n,K_n) (n,A0,K1,A1,...,An,Kn)
-
非终端节点的子树个数: ⌈ m / 2 ⌉ ≤ n ≤ m ⌈m/2⌉\leq n \leq m ⌈m/2⌉≤n≤m
关键字个数: ⌈ m / 2 ⌉ − 1 ≤ n ′ ≤ m − 1 ⌈m/2⌉ -1\leq n' \leq m-1 ⌈m/2⌉−1≤n′≤m−1
2. 插入
插入叶子节点的关键字个数 ≤ m − 1 \leq m-1 ≤m−1,时,直接插入,否则进行分裂。
3. 删除
B+树
略略
2. 哈希查找
查找or存储:哈希函数+冲突处理
1) 哈希函数:从key直接计算地址
-
直接定址法:双射
-
平方取中法:以关键字的平方值的中间几位作为存储地址
-
随机数法: H ( k e y ) = R a n d o m ( k e y ) H(key) = Random(key) H(key)=Random(key)
-
数字分析法:寻找关键字的数字特征
-
折叠法:叠加关键字的不同部分
-
除留余数法:
H ( k e y ) = k e y m o d p , p ≤ m H(key) = key\mod p, p\leq m H(key)=keymodp,p≤m
m为表长,p应为素数或者不含20一下的质因子
2) 处理冲突
-
冲突原因:哈希函数无法保证不同的关键字得到不同的哈希地址
-
处理方法:
-
开放定址法:产生冲突时,地址按照特定规律偏移,比如:
-
线性探测:1, 2, 3, …
-
平方探测:1, -1, 4, -4, 9, -9, …
-
伪随机探测:利用特定种子生成的随机数列
-
-
链地址法:将所有哈希地址相同的记录都链接在同一链表中
例: H ( k e y ) = k e y m o d 7 H(key) = key \mod 7 H(key)=keymod7
-
再哈希法:当 H i H_i Hi产生冲突时,调用 H i + 1 H_{i+1} Hi+1获得另一个地址
-
公共溢出区:哈希映射表+顺序排放的溢出区
-
-
影响ASL的因素
-
选用的哈希函数
-
处理冲突的方法
-
装填因子 α = R e c o r d C n t T a b l e L e n \alpha = \frac{RecordCnt}{TableLen} α=TableLenRecordCnt
-