Postgresql 为什么在';检查X最小值';标志设置为true?
我在postgres中有一个简单的表查询。我在那张表上有一个简单的索引 在某些环境中,它在执行查询时使用索引,而在其他环境中(在相同的RDS实例上,不同的数据库上)则不使用索引。(使用Postgresql 为什么在';检查X最小值';标志设置为true?,postgresql,Postgresql,我在postgres中有一个简单的表查询。我在那张表上有一个简单的索引 在某些环境中,它在执行查询时使用索引,而在其他环境中(在相同的RDS实例上,不同的数据库上)则不使用索引。(使用EXPLAIN analysis进行检查) 我注意到的一点是,如果索引上的“Check X Min”标志为TRUE,则不使用索引。(pg_catalog.pg_index.indcheckxmin) 我如何确保使用索引,并且假定“Check X Min”标志设置为false 表包含100K+行 我尝试过的事情:
EXPLAIN analysis
进行检查)
我注意到的一点是,如果索引上的“Check X Min”标志为TRUE,则不使用索引。(pg_catalog.pg_index.indcheckxmin
)
我如何确保使用索引,并且假定“Check X Min”标志设置为false
表包含100K+行
我尝试过的事情:
- 该索引是有效的,并且总是在“Check X Min”设置为false的环境中使用
将enable_seqscan设置为off代码>仍然不使用索引
- 在这些环境中创建/重新创建索引似乎总是将“Check X Min”设置为true
- 吸尘器似乎没有帮助
CREATE TABLE schema_1.table_1 (
field_1 varchar(20) NOT NULL,
field_2 int4 NULL,
field_3 timestamptz NULL,
field_4 numeric(10,2) NULL
);
CREATE INDEX table_1_field_1_field_3_idx ON schema_1.table_1 USING btree (field_1, field_3 DESC);
查询:
select field_1, field_2, field_3, field_4
from schema_1.table_1
where field_1 = ’abcdef’
order by field_3 desc limit 1;
不使用索引时:
QUERY PLAN |
---------------------------------------------------------------------------------------------------------------------|
Limit (cost=4.41..4.41 rows=1 width=51) (actual time=3.174..3.176 rows=1 loops=1) |
-> Sort (cost=4.41..4.42 rows=6 width=51) (actual time=3.174..3.174 rows=1 loops=1) |
Sort Key: field_3 DESC |
Sort Method: top-N heapsort Memory: 25kB |
-> Seq Scan on table_1 (cost=0.00..4.38 rows=6 width=51) (actual time=3.119..3.150 rows=3 loops=1)|
Filter: ((field_1)::text = 'abcdef'::text) |
Rows Removed by Filter: 96 |
Planning time: 2.895 ms |
Execution time: 3.197 ms |
QUERY PLAN |
--------------------------------------------------------------------------------------------------------------------------------------------------------|
Limit (cost=0.28..6.30 rows=1 width=51) (actual time=0.070..0.144 rows=1 loops=1) |
-> Index Scan using table_1_field_1_field_3_idx on field_1 (cost=0.28..12.31 rows=2 width=51) (actual time=0.049..0.066 rows=1 loops=1)|
Index Cond: ((field_1)::text = 'abcdef'::text) |
Planning time: 0.184 ms |
Execution time: 0.303 ms |
使用索引时:
QUERY PLAN |
---------------------------------------------------------------------------------------------------------------------|
Limit (cost=4.41..4.41 rows=1 width=51) (actual time=3.174..3.176 rows=1 loops=1) |
-> Sort (cost=4.41..4.42 rows=6 width=51) (actual time=3.174..3.174 rows=1 loops=1) |
Sort Key: field_3 DESC |
Sort Method: top-N heapsort Memory: 25kB |
-> Seq Scan on table_1 (cost=0.00..4.38 rows=6 width=51) (actual time=3.119..3.150 rows=3 loops=1)|
Filter: ((field_1)::text = 'abcdef'::text) |
Rows Removed by Filter: 96 |
Planning time: 2.895 ms |
Execution time: 3.197 ms |
QUERY PLAN |
--------------------------------------------------------------------------------------------------------------------------------------------------------|
Limit (cost=0.28..6.30 rows=1 width=51) (actual time=0.070..0.144 rows=1 loops=1) |
-> Index Scan using table_1_field_1_field_3_idx on field_1 (cost=0.28..12.31 rows=2 width=51) (actual time=0.049..0.066 rows=1 loops=1)|
Index Cond: ((field_1)::text = 'abcdef'::text) |
Planning time: 0.184 ms |
Execution time: 0.303 ms |
重命名了字段、架构和表以避免共享业务上下文您似乎在同时使用CREATE INDEX,并且有长时间打开的事务。发件人: 然而,即使这样,索引也可能不能立即用于查询:在最坏的情况下,只要在索引构建开始之前存在事务,就不能使用索引
你没有很多选择。查找并修复长时间打开的事务,不要同时使用或忍受限制。请显示查询、表和索引定义以及
解释输出。更新索引查询计划以使用相同的数据集并添加表大小(100K+行)在不使用索引的环境中,您的统计信息很可能已过时。运行vacuum是否分析schema_1.table_1代码>有什么变化吗?谢谢你的主意。我尝试了这个方法,但查询计划中没有任何更改-仍然没有使用索引。问题是什么?我意识到不使用索引的性能要比使用索引大一个数量级。但它仍然只有6毫秒(实际上稍微少一点)。这是10000次执行,以将总性能提高1分钟。我们应该梦想拥有追踪6ms低效率的系统。正如@jjanes所说,它只是“忍受限制”。换个大点的。