【问题标题】:Concat groups in SQL Server [duplicate]SQL Server 中的连接组 [重复]
【发布时间】:2010-10-30 18:40:33
【问题描述】:

如果我有这样的表:

+------------+
| Id | Value |
+------------+
| 1  | 'A'   |
|------------|
| 1  | 'B'   |
|------------|
| 2  | 'C'   |
+------------+

我怎样才能得到这样的结果集:

+------------+
| Id | Value |
+------------+
| 1  | 'AB'  |
|------------|
| 2  | 'C'   |
+------------+

我知道在 MySQL 中使用 GROUP_CONCAT 很容易做到这一点,但我需要能够在 MSSQL 2005 中做到这一点

谢谢

How to use GROUP BY to concatenate strings in SQL Server? 的重复)

【问题讨论】:

    标签: sql sql-server group-by string-concatenation


    【解决方案1】:

    要获得干净高效的解决方案,您可以创建 an user defined aggregate function,甚至还有 an example 可以满足您的需求。
    然后,您可以像使用任何其他聚合函数(使用标准查询计划)一样使用它:

    【讨论】:

    • 迄今为止最干净的解决方案
    【解决方案2】:

    这只是我想到的一种可能的解决方案。我对性能一无所知,但我认为这将是解决问题的一种有趣方式。我测试了它在一个简单的情况下工作(我没有编码来解释 NULL)。随意对其进行测试,看看它是否适合您。

    我使用的表包含一个 id (my_id)。这实际上可以是组中唯一的任何列 (grp_id),因此它可以是日期列或其他任何内容。

    ;WITH CTE AS (
        SELECT
            T1.my_id,
            T1.grp_id,
            CAST(T1.my_str AS VARCHAR) AS my_str
        FROM
            dbo.Test_Group_Concat T1
        WHERE NOT EXISTS (SELECT * FROM dbo.Test_Group_Concat T2 WHERE T2.grp_id = T1.grp_id AND T2.my_id < T1.my_id)
        UNION ALL
        SELECT
            T3.my_id,
            T3.grp_id,
            CAST(CTE.my_str + T3.my_str AS VARCHAR)
        FROM
            CTE
        INNER JOIN dbo.Test_Group_Concat T3 ON
            T3.grp_id = CTE.grp_id AND
            T3.my_id > CTE.my_id
        WHERE
            NOT EXISTS (SELECT * FROM dbo.Test_Group_Concat T4 WHERE
            T4.grp_id = CTE.grp_id AND
            T4.my_id > CTE.my_id AND
            T4.my_id < T3.my_id)
    )
    SELECT
        CTE.grp_id,
        CTE.my_str
    FROM
        CTE
    INNER JOIN (SELECT grp_id, MAX(my_id) AS my_id FROM CTE GROUP BY grp_id) SQ ON
        SQ.grp_id = CTE.grp_id AND
        SQ.my_id = CTE.my_id
    ORDER BY
        CTE.grp_id
    

    【讨论】:

      【解决方案3】:

      这样就可以了:

      SELECT mt.ID,
             SUBSTRING((SELECT mt2.Value
                        FROM   MyTable AS mt2
                        WHERE  mt2.ID = mt.ID
                        ORDER BY mt2.VALUE
                        FOR XML PATH('')), 3, 2000) AS JoinedValue
      FROM   MyTable AS mt
      

      【讨论】:

      • 这会连接 XML 文档中的值,这是不可取的。
      • 不,它使用 XML 函数。不涉及 XML 文档。为什么它“不受欢迎”?
      【解决方案4】:

      经常asked here

      最有效的方法是使用 FOR XML PATH 技巧。

      【讨论】:

      • 此外,我们在 SQL Server 中引入了 STRING_AGG(从 2017 年开始),它连接字符串表达式的值并在它们之间放置分隔符值(未添加在字符串的末尾)。 blog.vcillusion.co.in/…
      【解决方案5】:

      【讨论】:

      • 请查看我的博客,其中涵盖了 SQL Server 中分组连接的场景。 blog.vcillusion.co.in/…
      • 不使用带有 XML-PATH 的 Value 可能会导致 XML 编码值的解析错误。
      猜你喜欢
      • 2013-07-22
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2014-07-21
      • 1970-01-01
      • 2014-03-13
      • 2023-03-16
      相关资源
      最近更新 更多