【问题标题】:PostgreSQL - How to get the count of elements in a column listPostgreSQL - 如何获取列列表中的元素计数
【发布时间】:2016-11-25 11:53:37
【问题描述】:

这是我的订单表的样子:

-----------------------------------------------------------
| id  | order
-----------------------------------------------------------
|1    |[{"order_quantity" : 2, "active" : TRUE, "price" : $100 }, {"order_quantity" : 4, "active" : FALSE, "price" : $200 }]
|2    |[{"order_quantity" : 2, "active" : TRUE, "price" : $170 }]
|3    |[{"order_quantity" : 2, "active" : TRUE, "price" : $120 }]
|4    |[{"order_quantity" : 2, "active" : TRUE, "price" : $150 }, {"order_quantity" : 3, "active" : TRUE, "price" : $200 }, {"order_quantity" : 5, "active" : TRUE, "price" : $200 }]
-----------------------------------------------------------

计算每个元素中括号 WHERE active == TRUE 内的 JSON 元素时想要的结果:

------------
id  | counts
------------
|1  |   1
|2  |   1
|3  |   1
|4  |   3
------------

这是我正在使用的,但它没有提供我正在寻找的数据,因为它不会查看每个字典以查看 active == TRUE

SELECT id, json_array_length(order::JSON)
FROM orders

------------
id  | counts
------------
|1  |   2
|2  |   1
|3  |   1
|4  |   3
------------

【问题讨论】:

  • select id, array_length(string_to_array(orders::text, 'TRUE'), 1) - 1 as counts from ...

标签: json postgresql arraylist multiple-columns


【解决方案1】:

使用json_array_elements(),它选择json数组的所有元素,过滤元素,最后计算剩余元素按id分组。

select id, count(id)
from orders
cross join json_array_elements(orders) elem
where (elem->>'active')::boolean
group by 1
order by 1;

Db<>fiddle.现场演示

注意事项:

  • FROM 子句中使用集合返回函数(如json_array_elements())作为lateral join
  • json 布尔值应该类似于true(不是TRUE);
  • json中没有money类型,用300代替$300
  • 使用jsonlint 验证json 值。

【讨论】:

    【解决方案2】:

    我首先使用json_array_elements 对每个订单的订单进行规范化,然后能够进行计数并检查active = TRUE 是否存在

    WITH normalize_all_orders AS (
        SELECT id
           , json_array_elements(order::JSON) as order_line
        FROM orders
    )
    
    SELECT id
           , COUNT(order_line) AS orders_counts
    
    WHERE order_line::json->>'soundFlag' = 'true'
    GROUP BY id
    

    【讨论】:

    • +1 用于考虑数据规范化。顺便说一句,查询可以更简单,例如select id, (select count(*) from json_array_elements(order::JSON) as t(j) where j-&gt;&gt;'soundFlag' = 'true') as orders_counts from orders;(避免分组)。
    猜你喜欢
    • 1970-01-01
    • 2014-12-16
    • 2020-04-10
    • 1970-01-01
    • 2010-12-15
    • 2021-06-16
    • 1970-01-01
    • 2021-09-19
    • 1970-01-01
    相关资源
    最近更新 更多