← 中文资源

简体中文版本

索引选择性

选择性衡量索引条件过滤掉多少行。高基数谓词与合理排序的复合索引让查询高效;低选择性索引常不如扫描。

阅读英文原文

什么让索引有用

email 上的索引具有高选择性,因为大多数值唯一;active(true/false)则很低:查询活跃用户可能读取大部分表,规划器可能选择顺序扫描。

-- 高选择性:缩小到一行或少数行
CREATE INDEX orders_customer_created_idx
ON orders (customer_id, created_at DESC);

-- 单列低选择性;作为部分索引更有效
CREATE INDEX orders_pending_idx
ON orders (created_at)
WHERE status = 'pending';

复合索引顺序很重要

对于 WHERE tenant_id = $1 AND status = $2 ORDER BY created_at DESC,(tenant_id, status, created_at) 可以同时服务过滤与排序;(status, tenant_id, created_at) 在 status 低选择性时可能无法有效缩小范围。

测量而非猜测

EXPLAIN (ANALYZE, BUFFERS)
SELECT * FROM orders WHERE customer_id = $1 ORDER BY created_at DESC LIMIT 20;

关注索引扫描的 buffers 与行数。如果规划器选择顺序扫描,用 ANALYZE 更新统计信息,并比较实际行数与估算值。

何时添加索引

当查询频繁、选择性强且对延迟敏感时添加索引。与反规范化相比,索引保留数据模型但增加写入开销;与缓存相比,它优化源查询而不是复制结果。

陷阱

索引占用存储并拖慢插入、更新与删除。未使用的索引是纯开销,应审查使用统计。对索引列使用函数会阻止索引,除非建立匹配的表达式索引。用接近生产的数据分布测试;小表很少触发真实的规划器选择。