1

我有一个我通常的查询group_concat。我需要知道是否dbo.group_concat有能力将查询结果配对成 3 对(例如)。

例如:

select size, pattern, dbo.group_concat(mass) mass 
from labels 
group by size, pattern

结果是

Size Pattern Mass 
-----------------------------------------------------------
234  ZYL     22.43,55.32,33.24,22.53,56.32,40.32,50.21,32.21
234  ZA      50.00,56.23,21.23,50.21

我想要这个结果

Size Pattern  Mass
--------------------------------
234  ZYL      22.43,55.32,33.24
234  ZYL      22.53,56.32,40.32
234  ZYL      50.21,32.21
234  ZA       50.00,56.23,21.23
234  ZA       50.21 
4

1 回答 1

1

group ID如果我们有一个列,这可以很容易地完成。此列将每三行分组,按[mass]值对数据进行排序。由于我们没有这样的列,我们需要计算它。步骤如下:

  1. 我们正在使用ROW_NUMBER函数对行进行排序并知道哪三个结果行构成一个组
  2. 然后,我们使用递归公用表表达式(没什么太复杂的) - 只是获取每个size, pattern实体的第一行,然后加入下一行......然后加入下一行,直到我们得到所有实体

这是上述的完整工作示例:

DECLARE @DataSource TABLE
(
    [size] VARCHAR(12)
   ,[pattern] VARCHAR(12)
   ,[mass] DECIMAL(9,2)
);


INSERT INTO @DataSource ([size], [pattern], [mass])
VALUES (234, 'ZYL', 22.43)
      ,(234, 'ZYL', 55.32)
      ,(234, 'ZYL', 33.24)
      ,(234, 'ZYL', 22.53)
      ,(234, 'ZYL', 56.32)
      ,(234, 'ZYL', 40.32)
      ,(234, 'ZYL', 50.21)
      ,(234, 'ZYL', 32.21)
      --
      ,(234, 'ZA', 50.00)
      ,(234, 'ZA', 56.23)
      ,(234, 'ZA', 21.23)
      ,(234, 'ZA', 50.21);

WITH DataSource AS 
(
    SELECT *
          ,ROW_NUMBER() OVER (PARTITION BY [size], [pattern] ORDER BY [mass]) AS [RowID]
    FROM @DataSource
),
RecursiveDataSource AS
(
    SELECT [size], [pattern], [mass], [RowID]
          ,1 AS [Group]
    FROM DataSource
    WHERE [RowID] = 1
    UNION ALL
    SELECT A.*
          ,R.[Group] + CASE WHEN (A.[rowID] - 1) % 3 = 0 THEN 1 ELSE 0 END
    FROM DataSource A
    INNER JOIN RecursiveDataSource R
        ON A.[size] = R.[size]
        AND A.[pattern] = R.[pattern]
        AND A.[RowID] - 1 = R.[rowID]
)
SELECT *
FROM RecursiveDataSource
ORDER BY [pattern], [RowID];

在此处输入图像描述

现在,在最后SELECT我们只需要添加您的初始代码,但[group]也按列分组:

SELECT [size], [pattern], [dbo].[group_concat] ([mass])
FROM RecursiveDataSource
GROUP BY [size], [pattern], [Group];

在我的系统中,上面的结果如下:

在此处输入图像描述

一些考虑:

  • 我按值排序mass值(在您的示例中,您不是)-这完全取决于您;您可以将排序更改为您需要的任何内容,甚至可以SELECT 1在函数的ORDER BY子句中使用ROW_NUMBER以获得一些随机排序;
  • 对大表使用递归 CTE 会导致性能不佳;一定要先用你的真实数据测试过代码;
  • 我系统上的concatenateSQL CLR 功能允许设置顺序;就我而言,我已经使用该RowID值连接了行;如果您的函数不允许指定这样的顺序,则您依赖于它背后的 .net 代码,因此您可以在最终 CSV 列表中获得不同的值顺序。
于 2017-11-27T13:34:45.973 回答