受支持版本: 16 / 15 / 14

67.2. 实现 #

哈希索引中有四种页:元页(第零页),其中包含静态分配的控制信息;主桶页;溢出页;以及位图页,后者用于跟踪已被释放且可供重用的溢出页。在寻址时,位图页被视为溢出页的一个子集。

扫描索引和插入元组都需要定位给定元组应当所在的桶。为此,我们需要元页中的桶计数、highmask 和 lowmask;但是,出于性能原因,每次执行这类操作都去锁定并钉住元页并不理想。相反,我们在每个后端的 relcache 条目中保留元页的一个缓存副本。只要目标桶自上次缓存刷新以来没有被拆分,这就会产生正确的桶映射。

主桶页和溢出页是独立分配的,因为任何一个给定索引相对于其桶数,可能需要更多或更少的溢出页。哈希代码使用了一组颇有意思的寻址规则,以支持可变数量的溢出页,同时又不必在主桶页创建后再移动它们。

被索引表中的每一行,都由哈希索引中的单个索引元组表示。哈希索引元组存储在桶页中,如果存在溢出页,也会存储在溢出页中。为了加快搜索速度,我们将任一索引页中的索引项按哈希码排序,从而可以在索引页内使用二分查找。但请注意,并不假定同一桶中不同索引页之间的哈希码具有任何相对顺序。

用于扩展哈希索引的桶拆分算法过于复杂,这里不再展开说明;但在src/backend/access/hash/README中有更详细的描述。该拆分算法具备崩溃安全性,如果未能成功完成,可以重新启动。

提交更正

如果您发现文档中有不正确的内容、与您使用特定功能的经验不符或需要进一步说明,请使用此表单来报告文档问题。