gpt4 book ai didi

sql - group by 后将多行合并为一行

转载 作者:行者123 更新时间:2023-11-29 13:14:50 29 4
gpt4 key购买 nike

更新: https://www.db-fiddle.com/f/5fGUTSsAhGRPYPk33wDSzz/0

很抱歉提出了与上一个问题非常相似的问题,但我真的被困在这里了。

有多个表:

  • 项目 → items_roles → 角色
  • 项目 → 区域 → roles_zones → 角色

结构:

  • 项目:id,zone_id
  • items_roles: role_id, item_id
  • 区域:id
  • roles_zones: role_id, zone_id
  • 角色:id,role_type_id,

我正在尝试向项目添加角色字段,它应该采用 role_type 并且它是来自 items_zones 的值,如果它是 NULL,则从区域 (roles_zones) 获取回退值。

我开始于:

SELECT 
items.id,
(z_roles.role_type_id) as z_role_type_id,
(z_roles.id) as z_role_id,
MAX(i_roles.role_type_id) as i_role_type_id,
MAX(i_roles.id) as i_role_id
FROM
items
LEFT JOIN
zones as j_zones ON j_zones.id = items.zone_id
LEFT JOIN
roles_zones ON roles_zones.zone_id = j_zones.id
LEFT JOIN
roles as z_roles ON (z_roles.id = roles_zones.role_id)
LEFT JOIN
items_roles ON items_roles.item_id = items.id
LEFT JOIN
roles as i_roles ON items_roles.role_id = i_roles.id
AND (z_roles.role_type_id = i_roles.role_type_id)
WHERE
items.id = 834
GROUP BY
items.id, z_roles.role_type_id, z_roles.id
ORDER BY
i_role_id;

看起来不错:

id  |z_role_type_id |z_role_id |i_role_type_id |i_role_id |
----+---------------+----------+---------------+----------+
834 |5 |111 |5 |68 |
834 |11 |120 |11 |120 |
834 |7 |77 | | |
834 |2 |2 | | |
834 |12 |91 | | |
834 |4 |78 | | |
834 |8 |36 | | |

现在这个查询:

SELECT
items.id,
z_roles.role_type_id as z_role_type_id,
z_roles.id as z_role_id,
MAX(i_roles.role_type_id) AS i_role_type_id,
MAX(i_roles.id) AS i_role_id,
MAX(CASE
WHEN (i_roles.role_type_id = 5) THEN i_roles.id
WHEN (z_roles.role_type_id = 5) THEN z_roles.id
END) AS role_type_5_value,
MAX(CASE
WHEN (i_roles.role_type_id = 11) THEN i_roles.id
WHEN (z_roles.role_type_id = 11) THEN z_roles.id
END) AS role_type_11_value,
MAX(CASE
WHEN (i_roles.role_type_id = 7) THEN i_roles.id
WHEN (z_roles.role_type_id = 7) THEN z_roles.id
END) AS role_type_7_value
FROM
items
LEFT JOIN
zones AS j_zones ON j_zones.id = items.zone_id
LEFT JOIN
roles_zones ON roles_zones.zone_id = j_zones.id
LEFT JOIN
roles AS z_roles ON (z_roles.id = roles_zones.role_id)
LEFT JOIN
items_roles ON items_roles.item_id = items.id
LEFT JOIN
roles AS i_roles ON items_roles.role_id = i_roles.id
AND (z_roles.role_type_id = i_roles.role_type_id)
WHERE
items.id = 834
GROUP BY
items.id,
z_roles.role_type_id,
z_roles.id
ORDER BY
items.id, i_role_id;

生成这个:

 id  | z_role_type_id | z_role_id | i_role_type_id | i_role_id | role_type_5_value | role_type_11_value | role_type_7_value 
-----+----------------+-----------+----------------+-----------+-------------------+--------------------+-------------------
834 | 5 | 111 | 5 | 68 | 111 | |
834 | 11 | 120 | 11 | 120 | | 120 |
834 | 7 | 77 | | | | | 77
834 | 2 | 2 | | | | |
834 | 12 | 91 | | | | |
834 | 4 | 78 | | | | |
834 | 8 | 36 | | | | |
(7 rows)

role_type_5_value 有多行且值错误。可能是因为 MAX 聚合器。是否可以使用类似 first 聚合器的东西(因为按 i_role_id 排序的行和第一个结果是正确的)?

我想要这个:

 id  | role_type_5_value | role_type_11_value | role_type_7_value 
-----+-------------------+--------------------+-------------------
834 | 68 | 120 | 77

我试图通过聚合字段分组依据,(role_type_5_value, role_type_11_value, role_type_7_value) 但这是根本不起作用。

最佳答案

首先:从主查询中删除不需要的桥接表并将它们压缩到 EXISTS() 项中将简化您的查询。(您只需要三个表,其余的是胶水)

其次:不要将所有术语都放在 GROUP BY 子句中。


SELECT
i0.id
, MAX(CASE
WHEN (r1.role_type_id = 5) THEN r1.id
WHEN (r0.role_type_id = 5) THEN r0.id
END) AS role_type_5_value
, MAX(CASE
WHEN (r1.role_type_id = 11) THEN r1.id
WHEN (r0.role_type_id = 11) THEN r0.id
END) AS role_type_11_value
, MAX(CASE
WHEN (r1.role_type_id = 7) THEN r1.id
WHEN (r0.role_type_id = 7) THEN r0.id
END) AS role_type_7_value

FROM items i0
LEFT JOIN roles AS r0
ON EXISTS ( SELECT*
FROM zones AS z0
JOIN roles_zones rz ON rz.zone_id = z0.id
WHERE z0.id = i0.zone_id
AND r0.id = rz.role_id)

LEFT JOIN roles AS r1
ON EXISTS ( SELECT*
FROM items_roles ir
WHERE ir.item_id = i0.id
AND ir.role_id = r1.id
AND r0.role_type_id = r1.role_type_id
)

WHERE i0.id = 834
GROUP BY i0.id
-- r0.role_type_id,
-- r0.id
ORDER BY i0.id;

关于sql - group by 后将多行合并为一行,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/50420624/

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