postgres:为什么这个 GIN 索引不用于这个“数组中的对象”查询

Max*_* L. 3 postgresql jsonb

我正在尝试索引包含对象数组的 JSONB 列:

create table tmp_t (a INTEGER PRIMARY KEY,o jsonb);

insert into tmp_t (a,o)  values(1, '[{"frame": 1, "accession": "NM_001184642.1"}]');
insert into tmp_t (a,o)  values (2, '[{"frame": 3, "accession": "NM_001178208.1"}]');

CREATE INDEX idx_tmp_t ON tmp_t USING gin (o);
Run Code Online (Sandbox Code Playgroud)

EXPLAIN 告诉我以下查询不使用索引:

EXPLAIN
SELECT * from tmp_t v where v.o @> '[{"accession": "NM_001178208.1"}]';
Run Code Online (Sandbox Code Playgroud)

解释结果:

QUERY PLAN
Seq Scan on tmp_t v  (cost=0.00..1.02 rows=1 width=36)
  Filter: (o @> '[{""accession"": ""NM_001178208.1""}]'::jsonb)
Run Code Online (Sandbox Code Playgroud)

我的设置似乎与回答这个问题时给出的设置相同:

在 PostgreSQL 中使用 json 数组中的索引

我在问题中创建了示例表,并且确实使用了索引:

"QUERY PLAN"
"Bitmap Heap Scan on tracks  (cost=16.01..20.02 rows=1 width=36)"
"  Recheck Cond: (artists @> '[{""z"": 2}]'::jsonb)"
"  ->  Bitmap Index Scan on tracks_artists_gin_idx  (cost=0.00..16.01 rows=1 width=0)"
"        Index Cond: (artists @> '[{""z"": 2}]'::jsonb)"
Run Code Online (Sandbox Code Playgroud)

kli*_*lin 9

实际使用索引,只是使用更大的测试数据。

计划者可以根据数据选择不同的计划。通常情况下,规划器不会在行数较少的数据集上使用索引,而是在数据量增加时开始使用它。