【问题标题】:PostgreSQL jsonb_array_elements with array of Hash elements带有哈希元素数组的 PostgreSQL jsonb_array_elements
【发布时间】:2016-04-20 02:30:52
【问题描述】:

我有一个 PostgreSQL 表(生物),如下所示:

| id <integer> | json <jsonb> |
-------------------------------
|      1       | {"name": "Grooper", "weaknesses":[{"type":"Fire", "value":2},{"type":"Dark", "value":2}]} |
|      2       | {"name": "Zik", "weaknesses":[{"type":"Fire", "value":2}]} |

我正在尝试创建一个过滤弱点类型的查询,这样我就可以过滤所有具有弱点类型的生物 Fire Dark(包含任何一个),但也查询具有Fire Dark 类型弱点的生物(必须同时包含两者)。

我找到了一个适用于Fire Dark的查询:

select 
  distinct c.* 
from 
  creatures c, 
  jsonb_array_elements(json->'weaknesses') as weakness 
where weakness->'type' ?| array['Fire','Dark']

我怎样才能让这个查询过滤Fire Dark类型的生物?

更新:

我有一个查询似乎可以完成我想要的,但它看起来并不漂亮。有什么建议吗?

SELECT * FROM creatures
WHERE 'Fire' in (SELECT jsonb_array_elements(json->'weaknesses')->>'type') 
AND 'Dark' in (SELECT jsonb_array_elements(json->'weaknesses')->>'type')

【问题讨论】:

    标签: postgresql postgresql-9.4 jsonb


    【解决方案1】:

    这里的问题是您必须“查看”数组内的jsonb 值,因此您不能使用?&amp; 运算符。相反,使用 ? 运算符找到适当的键,并仅选择那些具有两次命中的行:

    SELECT DISTINCT id, json
    FROM creatures
    JOIN LATERAL jsonb_array_elements(json->'weaknesses') ON value ? 'Dark' OR value ? 'Fire'
    GROUP BY 1, 2
    HAVING count(id) = 2;
    

    顺便说一句,如果id 是唯一的(也许是主键?),那么SELECT DISTINCT ON (id) id, json ... 会快得多,因为不必检查jsonb 文档以删除重复项。

    【讨论】:

      猜你喜欢
      • 2020-07-19
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2021-08-01
      • 2011-12-14
      相关资源
      最近更新 更多