Linear Hashing 中分裂指针的作用和原理
1. 为什么需要分裂指针?
在 Linear Hashing(线性哈希) 中,桶溢出(Bucket Overflow) 是由于某个桶存储过多数据而无法继续插入。与 Extendible Hashing 不同,Linear Hashing 不会直接扩展所有桶,而是选择顺序分裂桶,由**分裂指针(Split Pointer)**控制。
目的:
- 有序分裂:分裂过程有序,不需要动态管理复杂的深度。
- 均匀扩展:按顺序分裂可以逐步分散数据,而不是立即影响整个表。
2. 分裂指针为什么要移动到下一个桶?
当一个桶被分裂后,指针会移动到下一个桶。这是 Linear Hashing 的核心设计:
- 分裂指针确保每次只分裂一个桶,按顺序扩展哈希表。
- 下一个桶也有可能溢出,需要分裂;即使不满,也会按照规则逐一处理。
核心原理:分裂是渐进的,不是全局的!
-
避免全局重建:
- 如果每次扩展都对所有桶重新分配数据,成本会很高。
- 分裂指针确保数据扩展是局部的,只影响当前桶。
-
数据的动态重分配:
- 假设原始哈希规则是
hash(key) % n
,分裂后会增加新规则hash(key) % 2n
。 - 新规则会将数据动态重分配到旧桶或新桶。
- 指针顺序分裂,保证分裂过程是渐进的、可控的。
- 假设原始哈希规则是
3. 分裂指针的具体流程
假设:
- 初始哈希规则:
hash(key) % 4
(总桶数 = 4)。 - 插入数据后,第 0 号桶溢出。
步骤:
-
分裂当前桶(第 0 号桶):
- 重新计算该桶中的数据,按照
hash(key) % 8
的新规则分配。 - 部分数据仍留在第 0 号桶,另一部分数据被分配到新增的第 4 号桶。
- 重新计算该桶中的数据,按照
-
移动分裂指针到下一个桶(第 1 号桶):
- 指针顺序移动到第 1 号桶,继续观察该桶是否需要分裂。
- 如果桶未满,则不分裂,指针继续移动。
-
逐步分裂其他桶:
- 每次只分裂一个桶,最终所有桶都会被重新分配。
4. 为什么要顺序分裂?
核心思想:分裂是逐步扩展容量的过程。
-
保证数据的平衡分布:
- 顺序分裂能逐渐将数据均匀分布到更多桶中,而不会一次性改变整个哈希表。
-
控制性能开销