【发布时间】:2021-12-29 08:19:19
【问题描述】:
我有一张如下表:
create table Configuration(
config_id varchar,
configurations jsonb
)
示例配置列如下所示:
{
"orderProcessing":{
"limit":3000,
"config1":false,
"config2":true,
"config3": "Example Text"
}
}
注意:“orderProcessing”和“limit”不是配置的必填字段,在某些行中会丢失。
我创建了一个这样的 Btree 索引:
create index id_limit_idx on configuration(config_id, (configurations->'orderProcessing'->>'limit'));
我需要像这样基于 orderProcessing.limit 进行聚合:
select configurations->'orderProcessing'->>'limit', count(*)
from configuration
where config_id = 'some_id'
GROUP BY (configurations->'orderProcessing'->>'limit')
但是查询没有使用 id_limit_idx 索引,而是进行了顺序扫描。
-------------------------------------------------------------------------------------------------------------------------------------------------------
Finalize GroupAggregate (cost=143843.65..143857.83 rows=22 width=40) (actual time=100.556..102.656 rows=6 loops=1)
Group Key: (((configurations -> 'orderProcessing'::text) ->> 'limit'::text))
-> Gather Merge (cost=143843.65..143856.95 rows=110 width=40) (actual time=100.545..102.639 rows=27 loops=1)
Workers Planned: 5
Workers Launched: 5
-> Sort (cost=142843.57..142843.62 rows=22 width=40) (actual time=96.222..96.224 rows=4 loops=6)
Sort Key: (((configurations -> 'orderProcessing'::text) ->> 'limit'::text))
Sort Method: quicksort Memory: 25kB
Worker 0: Sort Method: quicksort Memory: 25kB
Worker 1: Sort Method: quicksort Memory: 25kB
Worker 2: Sort Method: quicksort Memory: 25kB
Worker 3: Sort Method: quicksort Memory: 25kB
Worker 4: Sort Method: quicksort Memory: 25kB
-> Partial HashAggregate (cost=142842.75..142843.08 rows=22 width=40) (actual time=96.185..96.187 rows=4 loops=6)
Group Key: ((configurations -> 'orderProcessing'::text) ->> 'limit'::text)
-> Parallel Seq Scan on configuration (cost=0.00..142544.62 rows=59626 width=32) (actual time=5.988..86.741 rows=48976 loops=6)
Filter: (config_id = 'some_id'::text)
Rows Removed by Filter: 279276
Planning Time: 0.103 ms
Execution Time: 102.699 ms
(20 rows)
这让我怀疑我创建的索引不正确。也许我所做的不是在 json 元素的嵌套字段上创建索引的正确方法。
非常感谢这里的任何帮助。
【问题讨论】:
-
"查询没有使用 id_limit_idx 索引" - 它显然可以在步骤
Bitmap Index Scan on id_limit_idx中看到 - 我没有看到任何 Seq Scan计划。 -
@a_horse_with_no_name 我提供的查询计划是在我通过设置
SET enable_seqscan = OFF强制它使用索引之后。这就是没有 Seq 扫描的原因。但正如您所见,它仍在运行Parallel Bitmap Heap Scan。所以,问题是为什么需要这一步,因为所需的信息已经是索引的一部分 -
显示使用 Seq Scan 的人会更好地理解为什么会发生这种情况。
-
@a_horse_with_no_name 我无法将其粘贴到评论中。因此,更新了原始问题中的查询计划。请看一看。
-
@user14870583 好。切勿为请求的信息创建评论。 总是更新实际问题。然后,如果您认为有必要通知请求者,您可以发表评论表明已完成。
标签: sql postgresql indexing query-optimization