如何动态添加列?

时间:2018-09-24 14:19:58

标签: sql-server tsql sql-server-2008

我有以下数据用于计算每日活动。数字列每天都会变化,例如,第一天可以是1到5,第二天是1到8,第三天是1到10,依此类推。因此,我使用了动态数据透视表来获取列并将其插入到临时表中。 #没有。从表中我想将1到Nth列的值相加以获得总计。

数据

CREATE TABLE ##TBL (Number INT, Months VARCHAR(10), Total INT)
INSERT INTO ##TBL VALUES
(3,'Dec',1),(10,'Dec',1),(8,'Dec',1),(6,'Mar',1),(9,'Mar',1),(6,'Mar',1),(3,'Dec',1),(5,'Mar',1),(3,'Mar',1),
(2,'Mar',1),(10,'Dec',1),(7,'Mar',1),(3,'Mar',1),(6,'Dec',1),(4,'Mar',1),(9,'Dec',1),(1,'Mar',1),(3,'Mar',1),
(5,'Dec',1),(9,'Dec',1),(5,'Mar',1),(8,'Mar',1),(7,'Mar',1),(5,'Mar',1),(4,'Mar',1),(8,'Mar',1),(3,'Mar',1),
(7,'Mar',1),(5,'Mar',1),(2,'Mar',1),(6,'Mar',1),(2,'Mar',1),(8,'Dec',1),(1,'Mar',1),(5,'Mar',1),(6,'Mar',1),
(8,'Mar',1),(3,'Mar',1),(9,'Dec',1),(5,'Dec',1),(8,'Dec',1),(7,'Dec',1),
(5,'Dec',1)

数据透视表产生输出

DECLARE @Numb AS NVARCHAR(MAX),
        @query  AS NVARCHAR(MAX);

SET @Numb =(SELECT SUBSTRING(
(
    SELECT distinct', ' + QUOTENAME(Number) AS 'data()'
        FROM ##TBL
        FOR XML PATH('')        
), 2 , 9999) As nums)

SET @query =
'SELECT * 
INTO ##NO
FROM ##TBL
        PIVOT
        ( SUM(Total) FOR Number IN ('+@Numb+')) PV'

EXEC (@query)
SELECT 
*,
ISNULL([1],0)+ISNULL([2],0)+ISNULL([3],0)+ISNULL([4],0)+ISNULL([5],0)+ISNULL([6],0)+ISNULL([7],0)+
ISNULL([8],0)+ISNULL([9],0)+ISNULL([10],0) AS Grand_Total

FROM ##NO
DROP TABLE ##NO

当前输出

Months  1    10  2    3  4    5 6   7   8   9   Grand_Total
 Dec    NULL 2   NULL 2  NULL 3 1   1   3   3    15
 Mar    2   NULL 3    5  2    5 4   3   3   1    28

有没有一种方法可以在列的末尾增加或减少时动态求和? 列始终从1,2,3….n开始,我并不真正担心列顺序

期望的第一天输出

Months  1     2     3   4     5  Grand_Total
Dec     NULL  NULL  2   NULL  3  5
Mar     2     3     5   2     5  17

期望的输出日2

Months  1   2     3  Grand_Total        
Dec    NULL NULL  2  2      
Mar     2   3     5  10     

当数字列数据增加或减少时,我想要的是什么。我希望能够将它们加起来。有时数字从1到5结束,另一个时间是1到7,另一个时间是1到8,等等。

1 个答案:

答案 0 :(得分:3)

您可以使用它来动态获取总和。

declare @SUM nvarchar(max) = ''

SELECT @SUM = @SUM + 'ISNULL(' + QUOTENAME(Number) + ',0)+'
FROM ##TBL
group by Number

select @SUM = left(@SUM, len(@SUM) - 1)

然后将其添加到查询中非常简单。

SET @query =
'SELECT *, Grand_Total = ' + @SUM
+ 'INTO ##NO
FROM ##TBL
        PIVOT
        ( SUM(Total) FOR Number IN ('+@Numb+')) PV'

因此完整的功能代码如下所示。

CREATE TABLE ##TBL (Number INT, Months VARCHAR(10), Total INT)
INSERT INTO ##TBL VALUES
(3,'Dec',1),(10,'Dec',1),(8,'Dec',1),(6,'Mar',1),(9,'Mar',1),(6,'Mar',1),(3,'Dec',1),(5,'Mar',1),(3,'Mar',1),
(2,'Mar',1),(10,'Dec',1),(7,'Mar',1),(3,'Mar',1),(6,'Dec',1),(4,'Mar',1),(9,'Dec',1),(1,'Mar',1),(3,'Mar',1),
(5,'Dec',1),(9,'Dec',1),(5,'Mar',1),(8,'Mar',1),(7,'Mar',1),(5,'Mar',1),(4,'Mar',1),(8,'Mar',1),(3,'Mar',1),
(7,'Mar',1),(5,'Mar',1),(2,'Mar',1),(6,'Mar',1),(2,'Mar',1),(8,'Dec',1),(1,'Mar',1),(5,'Mar',1),(6,'Mar',1),
(8,'Mar',1),(3,'Mar',1),(9,'Dec',1),(5,'Dec',1),(8,'Dec',1),(7,'Dec',1),
(5,'Dec',1)

DECLARE @Numb AS NVARCHAR(MAX),
        @query  AS NVARCHAR(MAX);

SET @Numb =(SELECT SUBSTRING(
(
    SELECT distinct', ' + QUOTENAME(Number) AS 'data()'
        FROM ##TBL
        FOR XML PATH('')        
), 2 , 9999) As nums)

declare @SUM nvarchar(max) = ''

SELECT @SUM = @SUM + 'ISNULL(' + QUOTENAME(Number) + ',0)+'
FROM ##TBL
group by Number


select @SUM = left(@SUM, len(@SUM) - 1)

SET @query =
'SELECT *, Grand_Total = ' + @SUM
+ 'INTO ##NO
FROM ##TBL
        PIVOT
        ( SUM(Total) FOR Number IN ('+@Numb+')) PV'

select @query

EXEC (@query)

select * from ##NO

DROP TABLE ##NO

drop table ##TBL