This question already has an answer here:
Is there any function in oracle similar to group_concat in mysql? [duplicate]

(1个答案)


6年前关闭。





我看到了前面的问题,其中表的列为“ No”和“ Name”,而其他列则由数字列组成,但无法实现针对我的案例提供的答案。我需要做同样的事情,但要使用非数字分组。源表是带有以下列的tbl1:

POD    Name
---    -----
North  Rony
North  James
North  Aby
South  Sam
South  Willy
West   Mike


我需要进行以下聚合:

POD    Name
---    -----
North  Aby,James,Rony
South  Sam,Willy
West   Mike


由于“ POD”是非数字的,因此Msyma,Dinup和chetan先前的解决方案似乎对我不起作用。

我不知道如何将知识从他们的答案转移到这些要求上。

理想的查询是

SELECT POD, AGGREGATESTRING(Name)
FROM tbl1
GROUP BY POD


在理想的示例中,AGGREGATESTRING不会对人们的姓名进行排序,但是我认为我可以在需要的地方插入“ ORDER BY”。

最佳答案

Oracle 11g具有此整齐的函数LISTAGG,几乎是您想要的,但是由于您使用的是10g,因此它对您不可用(除非您决定升级)。

如果出于某种原因您不希望(或由于某些原因而无法)升级到11g,我建议您查看LISTAGG的一些替代品,这些替代品可用于10g。

您可以查看一些建议的替代方法here

快速调整建议的替代方案之一的快速适应方案,以适合您的案例方案:

WITH Q AS
(
    SELECT 'North' POD, 'Rony' NAME FROM DUAL  UNION ALL
    SELECT 'North',     'James'     FROM DUAL  UNION ALL
    SELECT 'North',     'Aby'       FROM DUAL  UNION ALL
    SELECT 'South',     'Sam'       FROM DUAL  UNION ALL
    SELECT 'South',     'Willy'     FROM DUAL  UNION ALL
    SELECT 'West',      'Mike'      FROM DUAL
)
SELECT   POD,
         RTRIM(
            XMLAGG (XMLELEMENT(e, name||',') ORDER BY name).EXTRACT('//text()'),
            ','
         ) AS name
    FROM q
GROUP BY POD;


但是请记住,这不是实际的解决方案,因为您必须根据表(而不是虚拟的DUAL表)来定制它……

您的解决方案可能看起来类似于以下内容:

SELECT   POD,
         RTRIM(
            XMLAGG (XMLELEMENT(E, NAME||',') ORDER BY NAME).EXTRACT('//text()'),
            ','
         ) AS NAME
    FROM tbl1
GROUP BY POD;


如果要更改定界符,可以在此部分用逗号将其更改:

(E, NAME||',')


RTRIM只是用来从串联字符串的末尾截断尾随逗号,如果您不被尾随逗号困扰,则可以省略RTRIM函数以保持可读性。

07-24 22:25