尽管 PostgreSQL 中的索引不需要维护或调整,但检查哪些索引实际上被实际查询工作负载使用仍然很重要。使用 EXPLAIN 命令检查单个查询的索引使用情况;其用于此目的的应用在 第 14.1 节 中进行了说明。还可以收集有关正在运行的服务器中索引使用情况的总体统计信息,如 第 28.2 节 中所述。
很难制定一个通用的过程来确定要创建哪些索引。在前面的章节中,已经展示了许多典型案例。通常需要进行大量的实验。本节的其余部分将提供一些提示
始终先运行 ANALYZE。此命令收集有关表中值分布的统计信息。需要此信息来估计查询返回的行数,而规划器需要此信息为每个可能的查询计划分配实际成本。在没有任何实际统计信息的情况下,将假定一些默认值,这些值几乎肯定是不准确的。因此,在没有运行 ANALYZE
的情况下检查应用程序的索引使用情况是徒劳的。有关更多信息,请参阅 第 25.1.3 节 和 第 25.1.6 节。
使用真实数据进行实验。使用测试数据设置索引将告诉你需要哪些索引来处理测试数据,但仅此而已。
使用非常小的测试数据集尤其致命。虽然从 100000 行中选择 1000 行可能是索引的候选,但从 100 行中选择 1 行几乎不可能,因为这 100 行可能只适合一个磁盘页,而且没有任何计划可以胜过顺序获取 1 个磁盘页。
在编制测试数据时也要小心,当应用程序尚未投入生产时,这通常是不可避免的。非常相似、完全随机或按排序顺序插入的值会使统计数据偏离真实数据所具有的分布。
当不使用索引时,强制使用索引可能有助于测试。有一些运行时参数可以关闭各种计划类型(请参阅 第 20.7.1 节)。例如,关闭顺序扫描(enable_seqscan
)和嵌套循环联接(enable_nestloop
),这是最基本的计划,将强制系统使用不同的计划。如果系统仍然选择顺序扫描或嵌套循环联接,那么可能有一个更根本的原因导致不使用索引;例如,查询条件与索引不匹配。(前几节解释了哪种类型的查询可以使用哪种类型的索引。)
如果强制使用索引确实使用了索引,那么有两种可能性:要么系统是正确的,并且使用索引实际上不合适,要么查询计划的成本估算并未反映现实。因此,你应该在有和没有索引的情况下对查询进行计时。EXPLAIN ANALYZE
命令在此处可能很有用。
如果发现成本估算错误,那么有两种可能性。总成本根据每个计划节点的每行成本乘以计划节点的选择性估算计算得出。计划节点的估算成本可以通过运行时参数(在第 20.7.2 节中描述)进行调整。不准确的选择性估算归因于统计信息不足。可以通过调整统计信息收集参数(请参阅ALTER TABLE)来改进这一点。
如果您未能调整成本以使其更合适,那么您可能必须诉诸于显式强制索引使用。您可能还希望联系PostgreSQL开发人员来检查此问题。