查询 Postgres JSONB 列中的多个数组元素
Query for multiple array elements in Postgres JSONB column
我有一个 table mydata jsonb 列,其中包含一个整数数组。
create table mydata
(
name varchar,
data jsonb
);
这里是一些测试数据:
insert into mydata (name, data)
VALUES
('hello1', '[1]'),
('hello12', '[1,2]'),
('hello2', '[2]'),
('hello23', '[2,3]')
;
我现在想在 table 中查询“数据”中包含 2 或 3(或两者)的元素。
除了:
之外还有更好的语法吗?
select * from mydata where (data @> '2' or data @> '3');
因为我当然可以查询 2 个以上的选项。我会假设我能够做这样的子查询(不工作,就像暗示我想要实现的那样):
create table other ( id bigserial , text varchar);
insert into other (id, text) values (1, 'x'), (2, 'y'), (3, 'y'), (4, 'z');
我现在想做的是,从 mydata 中获取所有数据,其中数据引用了 other_table
select * from mydata where (data @> IN (select distinct id from other_table where text='y'));
非常感谢,
弗里茨
SELECT DISTINCT -- 3
name,
data
FROM mydata,
jsonb_array_elements_text(data) elems -- 1
WHERE value::int IN (
SELECT id FROM other WHERE "text" = 'y' -- 2
)
- 将所有数组元素提取到自己的记录中
- 过滤之前的元素是否是子查询的元素
- 因为此过滤器可以 return 两次相同的记录(如果原始数据匹配
2
和 3
),DISTINCT
确保 return独特的记录。
如果 ID 来自不同的 table,您可以这样做:
select *
from mydata m
where exists (select *
from other o
where o.id in (select v::int
from jsonb_array_elements_text(m.data) as x(v)))
对于 Postgres 12 或更高版本,您可以使用
select *
from mydata m
where exists (select *
from other o
where jsonb_path_exists(m.data, '$[*] ? (@ == $id)', jsonb_build_object('id', o.id)))
不确定哪个会更快。
我有一个 table mydata jsonb 列,其中包含一个整数数组。
create table mydata
(
name varchar,
data jsonb
);
这里是一些测试数据:
insert into mydata (name, data)
VALUES
('hello1', '[1]'),
('hello12', '[1,2]'),
('hello2', '[2]'),
('hello23', '[2,3]')
;
我现在想在 table 中查询“数据”中包含 2 或 3(或两者)的元素。 除了:
之外还有更好的语法吗?select * from mydata where (data @> '2' or data @> '3');
因为我当然可以查询 2 个以上的选项。我会假设我能够做这样的子查询(不工作,就像暗示我想要实现的那样):
create table other ( id bigserial , text varchar);
insert into other (id, text) values (1, 'x'), (2, 'y'), (3, 'y'), (4, 'z');
我现在想做的是,从 mydata 中获取所有数据,其中数据引用了 other_table
select * from mydata where (data @> IN (select distinct id from other_table where text='y'));
非常感谢, 弗里茨
SELECT DISTINCT -- 3
name,
data
FROM mydata,
jsonb_array_elements_text(data) elems -- 1
WHERE value::int IN (
SELECT id FROM other WHERE "text" = 'y' -- 2
)
- 将所有数组元素提取到自己的记录中
- 过滤之前的元素是否是子查询的元素
- 因为此过滤器可以 return 两次相同的记录(如果原始数据匹配
2
和3
),DISTINCT
确保 return独特的记录。
如果 ID 来自不同的 table,您可以这样做:
select *
from mydata m
where exists (select *
from other o
where o.id in (select v::int
from jsonb_array_elements_text(m.data) as x(v)))
对于 Postgres 12 或更高版本,您可以使用
select *
from mydata m
where exists (select *
from other o
where jsonb_path_exists(m.data, '$[*] ? (@ == $id)', jsonb_build_object('id', o.id)))
不确定哪个会更快。