在sql server中选择每10行作为新列

在sql server中选择每10行作为新列,sql,sql-server,group-by,Sql,Sql Server,Group By,我有一个包含数据的SQL表,如图所示 Item Qty ------------ A1 59 A2 76 A3 86 A1 12 A2 17 A3 15 A1 23 A2 39 A3 07 在这里我们可以看到项目是重复的。所以,我想按项目对记录进行分组。 我想得到如下所示的输出表 Item Qty1 Qty2 qty3 ------------------

我有一个包含数据的SQL表,如图所示

Item     Qty
------------
A1       59
A2       76
A3       86
A1       12
A2       17
A3       15
A1       23
A2       39
A3       07
在这里我们可以看到项目是重复的。所以,我想按项目对记录进行分组。 我想得到如下所示的输出表

 Item    Qty1     Qty2     qty3
----------------------------------
    A1      59       12       23
    A2      76       17       39
    A3      86       15       07

使用带有排名功能的
pivot
行数

WITH CTE
AS
(

    SELECT 
      Item, QTy, ROW_NUMBER() OVER(PARTITION BY ITem ORDER BY Item) AS RN
    FROM tablename

)
SELECT Item, [1] AS Qty1, [2] AS Qty2, [3] AS Qty3
FROM CTE
PIVOT
(
    SUM(Qty)
    FOR rn IN([1], [2], [3])
) AS p;
结果:

| Item | Qty1 | Qty2 | Qty3 |
|------|------|------|------|
|   A1 |   59 |   12 |   23 |
|   A2 |   39 |   17 |   76 |
|   A3 |   86 |   15 |    7 |

如果这些数量不是固定的,并且它们并非始终为3,则需要像这样动态执行:

DECLARE @cols AS NVARCHAR(MAX);
DECLARE @query AS NVARCHAR(MAX);
DECLARE @colNames AS NVARCHAR(MaX);


select @cols = STUFF((SELECT distinct ',' +
                QUOTENAME(CAST(RN AS NVARCHAR(10)))
                      FROM
                      (
                        SELECT 
      Item, QTy, ROW_NUMBER() OVER(PARTITION BY ITem ORDER BY Item) AS RN
    FROM tablename ) as t
                      FOR XML PATH(''), TYPE
                     ).value('.', 'NVARCHAR(MAX)') 
                        , 1, 1, '');

select @colNames = STUFF((SELECT distinct ',' +
                '[' + CAST(RN AS NVARCHAR(10)) + '] AS Qty' + 
                         CAST(RN AS NVARCHAR(10))
                      FROM
                      (
                        SELECT 
      Item, QTy, ROW_NUMBER() OVER(PARTITION BY ITem ORDER BY Item) AS RN
    FROM tablename ) as t
                      FOR XML PATH(''), TYPE
                     ).value('.', 'NVARCHAR(MAX)') 
                        , 1, 1, '');


SELECT @query = 'WITH CTE
AS
(

    SELECT 
      Item, QTy, ROW_NUMBER() OVER(PARTITION BY ITem ORDER BY Item) AS RN
    FROM tablename

)
SELECT Item,' + @colNames + '
FROM CTE
PIVOT
(
    SUM(Qty)
    FOR rn IN(' + @cols + ')
) AS p;';

execute(@query);

使用带有排名功能的
行数

WITH CTE
AS
(

    SELECT 
      Item, QTy, ROW_NUMBER() OVER(PARTITION BY ITem ORDER BY Item) AS RN
    FROM tablename

)
SELECT Item, [1] AS Qty1, [2] AS Qty2, [3] AS Qty3
FROM CTE
PIVOT
(
    SUM(Qty)
    FOR rn IN([1], [2], [3])
) AS p;
结果:

| Item | Qty1 | Qty2 | Qty3 |
|------|------|------|------|
|   A1 |   59 |   12 |   23 |
|   A2 |   39 |   17 |   76 |
|   A3 |   86 |   15 |    7 |

如果这些数量不是固定的,并且它们并非始终为3,则需要像这样动态执行:

DECLARE @cols AS NVARCHAR(MAX);
DECLARE @query AS NVARCHAR(MAX);
DECLARE @colNames AS NVARCHAR(MaX);


select @cols = STUFF((SELECT distinct ',' +
                QUOTENAME(CAST(RN AS NVARCHAR(10)))
                      FROM
                      (
                        SELECT 
      Item, QTy, ROW_NUMBER() OVER(PARTITION BY ITem ORDER BY Item) AS RN
    FROM tablename ) as t
                      FOR XML PATH(''), TYPE
                     ).value('.', 'NVARCHAR(MAX)') 
                        , 1, 1, '');

select @colNames = STUFF((SELECT distinct ',' +
                '[' + CAST(RN AS NVARCHAR(10)) + '] AS Qty' + 
                         CAST(RN AS NVARCHAR(10))
                      FROM
                      (
                        SELECT 
      Item, QTy, ROW_NUMBER() OVER(PARTITION BY ITem ORDER BY Item) AS RN
    FROM tablename ) as t
                      FOR XML PATH(''), TYPE
                     ).value('.', 'NVARCHAR(MAX)') 
                        , 1, 1, '');


SELECT @query = 'WITH CTE
AS
(

    SELECT 
      Item, QTy, ROW_NUMBER() OVER(PARTITION BY ITem ORDER BY Item) AS RN
    FROM tablename

)
SELECT Item,' + @colNames + '
FROM CTE
PIVOT
(
    SUM(Qty)
    FOR rn IN(' + @cols + ')
) AS p;';

execute(@query);

您可以按如下方式使用pivot:

Select * from (
    Select *, Qtys = Concat('Qty', Row_Number() over(partition by Item order by Item))
        from #itemdata
        ) a
    pivot (max(qty) for qtys in ([Qty1],[Qty2],[Qty3])) p
Declare @cols1 varchar(max)
Declare @query nvarchar(max)

Select @cols1 = stuff((select top (select max(cnt) from (select count(*) cnt from #itemdata group by item ) a) ','+
    QuoteName(Concat('Qty', Row_Number() over(order by (select Null)))) from 
    master..spt_values c1, master..spt_values c2  for xml path('')),1,1,'')

Select @query = ' Select * from (
    Select *, Qtys = Concat(''Qty'', Row_Number() over(partition by Item order by Item))
            from #itemdata
        ) a
    pivot (max(qty) for qtys in (' + @cols1 + ')) p '

Exec sp_executesql @query
对于动态列表,您可以按如下方式查询:

Select * from (
    Select *, Qtys = Concat('Qty', Row_Number() over(partition by Item order by Item))
        from #itemdata
        ) a
    pivot (max(qty) for qtys in ([Qty1],[Qty2],[Qty3])) p
Declare @cols1 varchar(max)
Declare @query nvarchar(max)

Select @cols1 = stuff((select top (select max(cnt) from (select count(*) cnt from #itemdata group by item ) a) ','+
    QuoteName(Concat('Qty', Row_Number() over(order by (select Null)))) from 
    master..spt_values c1, master..spt_values c2  for xml path('')),1,1,'')

Select @query = ' Select * from (
    Select *, Qtys = Concat(''Qty'', Row_Number() over(partition by Item order by Item))
            from #itemdata
        ) a
    pivot (max(qty) for qtys in (' + @cols1 + ')) p '

Exec sp_executesql @query

您可以按如下方式使用pivot:

Select * from (
    Select *, Qtys = Concat('Qty', Row_Number() over(partition by Item order by Item))
        from #itemdata
        ) a
    pivot (max(qty) for qtys in ([Qty1],[Qty2],[Qty3])) p
Declare @cols1 varchar(max)
Declare @query nvarchar(max)

Select @cols1 = stuff((select top (select max(cnt) from (select count(*) cnt from #itemdata group by item ) a) ','+
    QuoteName(Concat('Qty', Row_Number() over(order by (select Null)))) from 
    master..spt_values c1, master..spt_values c2  for xml path('')),1,1,'')

Select @query = ' Select * from (
    Select *, Qtys = Concat(''Qty'', Row_Number() over(partition by Item order by Item))
            from #itemdata
        ) a
    pivot (max(qty) for qtys in (' + @cols1 + ')) p '

Exec sp_executesql @query
对于动态列表,您可以按如下方式查询:

Select * from (
    Select *, Qtys = Concat('Qty', Row_Number() over(partition by Item order by Item))
        from #itemdata
        ) a
    pivot (max(qty) for qtys in ([Qty1],[Qty2],[Qty3])) p
Declare @cols1 varchar(max)
Declare @query nvarchar(max)

Select @cols1 = stuff((select top (select max(cnt) from (select count(*) cnt from #itemdata group by item ) a) ','+
    QuoteName(Concat('Qty', Row_Number() over(order by (select Null)))) from 
    master..spt_values c1, master..spt_values c2  for xml path('')),1,1,'')

Select @query = ' Select * from (
    Select *, Qtys = Concat(''Qty'', Row_Number() over(partition by Item order by Item))
            from #itemdata
        ) a
    pivot (max(qty) for qtys in (' + @cols1 + ')) p '

Exec sp_executesql @query

是否总是有3个数量atmost?例如,为什么59是
Qty1
而不是
Qty3
?是否总是有3个数量atmost?例如,为什么59是
Qty1
而不是
Qty3