gpt4 book ai didi

jsonb[] vs jsonb 其中json是一个数组

转载 作者:行者123 更新时间:2023-11-29 12:49:59 27 4
gpt4 key购买 nike

我有一个 Postgres 表,mytable 其中一个字段如下:

myField JSONB[] NOT NULL

让我们假设上述 json 是这种形式:

{ "字母":"A", "数字":30}

我应该使用什么查询:

  • 提取 digit 值的数组?
  • 提取包含 digit 值的 json 数组?
  • 提取 digit 值的数组,其中 digit > 20?
  • 提取 digit 值的 json 数组,其中 digit > 20?

如果我将数据存储为 json,其中 json 是一个列表,上述查询会发生什么变化?

  • 我还能进行上述所有查询吗?
  • 性能差异是什么?
  • 我应该在什么时候选择其中之一?

最佳答案

让我们创建一个表,它有一个名为 pg_arrayjsonb[] 列,它将存储一个数组 JSON 对象和一个 jsonb< 类型的列 调用了 json_array,它将存储对象的 JSON 数组:

CREATE TABLE mytable (id int, pg_array jsonb[], json_array jsonb);
INSERT INTO mytable VALUES
(1, ARRAY['{"letter":"A", "digit":30}', '{"letter":"B", "digit":31}']::jsonb[], '[{"letter":"A", "digit":30},{"letter":"B", "digit":31}]'),
(2, ARRAY['{"letter":"X", "digit":40}', '{"letter":"Y", "digit":41}']::jsonb[], '[{"letter":"X", "digit":40},{"letter":"Y", "digit":41}]');

这两种方法的查询看起来非常相似,因为我们将处理单个数组元素,这意味着我们必须再次取消嵌套和聚合。

取消嵌套 pg_array 并获取每个 jsonb 对象:

SELECT unnest(pg_array);

取消嵌套 json_array 并获取每个 jsonb 对象:

SELECT jsonb_array_elements(json_array);

这是唯一的区别。因此,下面的查询看起来几乎相同。

关于你的第一组问题:

extract an array of the digit values?

db=# SELECT array_agg((x->>'digit')::int) FROM mytable, unnest(pg_array) x GROUP BY id;
array_agg
-----------
{40,41}
{30,31}
(2 rows)
db=# SELECT array_agg((x->>'digit')::int) FROM mytable, jsonb_array_elements(json_array) x GROUP BY id;
array_agg
-----------
{40,41}
{30,31}
(2 rows)

extract a json array containing the digit values?

db=# SELECT jsonb_agg((x->>'digit')::int) FROM mytable, unnest(pg_array) x GROUP BY id;
jsonb_agg
-----------
[40, 41]
[30, 31]
(2 rows)
db=# SELECT jsonb_agg((x->>'digit')::int) FROM mytable, jsonb_array_elements(json_array) x GROUP BY id;
jsonb_agg
-----------
[40, 41]
[30, 31]
(2 rows)

extract an array of the digit values where digit > 20?

(我在这里使用了 30 而不是 20。)

db=# SELECT array_agg((x->>'digit')::int) FROM mytable, unnest(pg_array) x WHERE (x->>'digit')::int > 30 GROUP BY id;
array_agg
-----------
{40,41}
{31}
(2 rows)
db=# SELECT array_agg((x->>'digit')::int) FROM mytable, jsonb_array_elements(json_array) x WHERE (x->>'digit')::int > 30 GROUP BY id;
array_agg
-----------
{40,41}
{31}
(2 rows)

extract a json array of the digit values where digit > 20?

(我在这里使用了 30 而不是 20。)

db=# SELECT jsonb_agg((x->>'digit')::int) FROM mytable, unnest(pg_array) x WHERE (x->>'digit')::int > 30 GROUP BY id;
jsonb_agg
-----------
[40, 41]
[31]
(2 rows)
db=# SELECT jsonb_agg((x->>'digit')::int) FROM mytable, jsonb_array_elements(json_array) x WHERE (x->>'digit')::int > 30 GROUP BY id;
jsonb_agg
-----------
[40, 41]
[31]
(2 rows)

第二组问题:

Can I still make all the above queries?

如上所示,是的。

What would be the performance difference?

这归结为 unnestjsonb_array_elements 的性能差异。让我们将其与包含具有 1,000,000 个 JSON 对象的数组的单行进行比较:

TRUNCATE mytable;
INSERT INTO mytable
SELECT 1, array_agg(o), jsonb_agg(o)
FROM (SELECT jsonb_build_object('letter', 'A', 'digit', i) o FROM generate_series(1, 1000000) i) x;
phil=# EXPLAIN ANALYZE SELECT unnest(pg_array) FROM mytable;
QUERY PLAN
-----------------------------------------------------------------------------------------------------------
ProjectSet (cost=0.00..35.88 rows=5000 width=32) (actual time=33.357..120.393 rows=1000000 loops=1)
-> Seq Scan on mytable (cost=0.00..10.50 rows=50 width=626) (actual time=0.010..0.013 rows=1 loops=1)
Planning time: 0.050 ms
Execution time: 175.670 ms
(4 rows)

phil=# EXPLAIN ANALYZE SELECT jsonb_array_elements(json_array) FROM mytable;
QUERY PLAN
-----------------------------------------------------------------------------------------------------------
ProjectSet (cost=0.00..35.88 rows=5000 width=32) (actual time=257.313..399.883 rows=1000000 loops=1)
-> Seq Scan on mytable (cost=0.00..10.50 rows=50 width=721) (actual time=0.010..0.014 rows=1 loops=1)
Planning time: 0.047 ms
Execution time: 455.275 ms
(4 rows)

由此看来 unnestjsonb_array_elements 快大约 2.5 倍。

When should I choose one over the other?

我假设您的数据集不够大,unnestjsonb_array_elements 之间的性能差异无法发挥作用。因此,我只会选择对数据更有意义的内容。我倾向于使用 jsonb[],因为它更清楚地表明您将拥有一个 json 对象数组。

关于jsonb[] vs jsonb 其中json是一个数组,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/56624552/

27 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com