可以在全文搜索中使用两种索引来提高速度:GIN 和 GiST。请注意,索引对全文搜索不是必须的,但是,当定期对某个列进行搜索时,通常需要提供索引。
要创建此类索引,请执行以下操作之一
GIN 索引是首选的文本搜索索引类型。作为反向索引,它们为每个单词(词素)包含一个索引条目,其中包含匹配位置的压缩列表。多单词搜索可以找到第一个匹配项,然后使用索引删除缺少其他单词的行。GIN 索引仅存储 tsvector
值的单词(词素),而不是它们的权重标签。因此,在使用涉及权重的查询时,需要对表行进行重新检查。
GiST 索引有损,这意味着索引可能会生成误匹配,而且有必要检查实际表格行以消除此类误匹配。(PostgreSQL 在需要时会自动执行此操作。)GiST 索引有损是因为每个文档在索引中由定长特征表示。字节中的特征长度由可选整数参数 siglen
的值确定。默认特征长度(siglen
未指定时)为 124 字节,最大特征长度为 2024 字节。特征是通过对每个单词哈希到 n 位字符串中的单一比特,将所有这些比特进行 OR 运算,以生成 n 位文档特征来生成的。当两个单词哈希到同一比特位置时,就会出现误匹配。如果查询中的所有单词均有匹配项(实际或误匹配),则必须检索表格行以查看匹配项是否正确。更长的特征会导致更精确的搜索(扫描索引的更小部分和更少的堆页),但代价是索引更大。
GiST 索引可以是覆盖索引,即使用 INCLUDE
子句。含括的列可以具有没有任何 GiST 运算符类的数据类型。含括的属性将以未压缩的形式存储。
有损会导致性能下降,因为不必要的表格记录提取结果为误匹配。由于对表格记录的随机访问很慢,这会限制 GiST 索引的实用性。误匹配的可能性取决于多个因素,特别是唯一单词的数量,因此建议使用词典来减少此数量。
请注意GIN索引生成时间可以通过增加 maintenance_work_mem 来提高,而GiST索引生成时间与该参数无关。
对大集合进行分区以及正确使用 GIN 和 GiST 索引可实施极其快速的在线更新搜索。可以使用表继承在数据库级别进行分区,或将文档分发到服务器,并收集外部搜索结果,例如,通过 外部数据 访问。之所以可行是因为排名函数只使用本地信息。