我正在努力解决问题。我想将行更改为列,但我不知道如何执行此操作。 Pivot是一个解决方案,但是没有按照我的要求提取列。这是一个例子。
上面的表格是我想要使用的表格,并将其转换为类似下面的表格
基本上,对于相同的请求ID,需要在同一行上分配多年。我曾尝试过 CASE ,但对于类似的事情来说,这似乎有些过分。
这是一个fiddle开头。
感谢。
答案 0 :(得分:2)
要获得完全弹性的解决方案,您应该搜索动态数据透视。如果您事先了解多年,可以使用:
;WITH cte AS
(
SELECT ReqId,quater1,quater2,quater3,quater4
,[q1] = CONCAT('Q1_',[year])
,[q2] = CONCAT('Q2_',[year])
,[q3] = CONCAT('Q3_',[year])
,[q4] = CONCAT('Q4_',[year])
FROM #forecast
)
SELECT ReqId
,[Q1_2014] = MAX([Q1_2014])
,[Q2_2014] = MAX([Q2_2014])
,[Q3_2014] = MAX([Q3_2014])
,[Q4_2014] = MAX([Q4_2014])
,[Q1_2015] = MAX([Q1_2015])
,[Q2_2015] = MAX([Q2_2015])
,[Q3_2015] = MAX([Q3_2015])
,[Q4_2015] = MAX([Q4_2015])
,[Q1_2016] = MAX([Q1_2016])
,[Q2_2016] = MAX([Q2_2016])
,[Q3_2016] = MAX([Q3_2016])
,[Q4_2016] = MAX([Q4_2016])
,[Q1_2017] = MAX([Q1_2017])
,[Q2_2017] = MAX([Q2_2017])
,[Q3_2017] = MAX([Q3_2017])
,[Q4_2017] = MAX([Q4_2017])
FROM cte
PIVOT (MAX(quater1) FOR [q1] IN ([Q1_2014],[Q1_2015],[Q1_2016],[Q1_2017])) AS pvt1
PIVOT (MAX(quater2) FOR [q2] IN ([Q2_2014],[Q2_2015],[Q2_2016],[Q2_2017])) AS pvt2
PIVOT (MAX(quater3) FOR [q3] IN ([Q3_2014],[Q3_2015],[Q3_2016],[Q3_2017])) AS pvt3
PIVOT (MAX(quater4) FOR [q4] IN ([Q4_2014],[Q4_2015],[Q4_2016],[Q4_2017])) AS pvt4
GROUP BY ReqId
的 LiveDemo
强>
输出:
╔════════╦══════════╦══════════╦══════════╦══════════╦══════════╦══════════╦══════════╦══════════╦══════════╦══════════╦══════════╦══════════╦══════════╦══════════╦══════════╦═════════╗
║ ReqId ║ Q1_2014 ║ Q2_2014 ║ Q3_2014 ║ Q4_2014 ║ Q1_2015 ║ Q2_2015 ║ Q3_2015 ║ Q4_2015 ║ Q1_2016 ║ Q2_2016 ║ Q3_2016 ║ Q4_2016 ║ Q1_2017 ║ Q2_2017 ║ Q3_2017 ║ Q4_2017 ║
╠════════╬══════════╬══════════╬══════════╬══════════╬══════════╬══════════╬══════════╬══════════╬══════════╬══════════╬══════════╬══════════╬══════════╬══════════╬══════════╬═════════╣
║ 1 ║ 10 ║ 20 ║ 30 ║ 40 ║ 50 ║ 60 ║ 70 ║ 80 ║ 90 ║ 100 ║ 110 ║ 120 ║ (null) ║ (null) ║ (null) ║ (null) ║
║ 2 ║ 10 ║ 20 ║ 30 ║ 40 ║ 50 ║ 60 ║ 70 ║ 80 ║ 90 ║ 100 ║ 110 ║ 120 ║ 130 ║ 140 ║ 150 ║ 160 ║
╚════════╩══════════╩══════════╩══════════╩══════════╩══════════╩══════════╩══════════╩══════════╩══════════╩══════════╩══════════╩══════════╩══════════╩══════════╩══════════╩═════════╝
可替换地:
;WITH cte AS (
SELECT ReqId, [q] ='Q1_' + CAST([year] AS CHAR(4)), quater = quater1 FROM #forecast
UNION ALL SELECT ReqId, [q] ='Q2_' + CAST([year] AS CHAR(4)), quater2 FROM #forecast
UNION ALL SELECT ReqId, [q] ='Q3_' + CAST([year] AS CHAR(4)), quater3 FROM #forecast
UNION ALL SELECT ReqId, [q] ='Q4_' + CAST([year] AS CHAR(4)), quater4 FROM #forecast
)
SELECT *
FROM cte
PIVOT (MAX(quater) FOR q IN (Q1_2014,Q2_2014,Q3_2014,Q4_2014,
Q1_2015,Q2_2015,Q3_2015,Q4_2015,
Q1_2016,Q2_2016,Q3_2016,Q4_2016,
Q1_2017,Q2_2017,Q3_2017,Q4_2017)
) AS pvt;
的 LiveDemo2
强>
Dynamic Pivot(您不需要提前知道几年):
DECLARE @sql NVARCHAR(MAX) = N'
WITH cte AS (
SELECT ReqId,[q] =''Q1_'' + CAST([year] AS CHAR(4)),quater = quater1 FROM #forecast
UNION ALL SELECT ReqId,[q] =''Q2_'' + CAST([year] AS CHAR(4)),quater2 FROM #forecast
UNION ALL SELECT ReqId,[q] =''Q3_'' + CAST([year] AS CHAR(4)),quater3 FROM #forecast
UNION ALL SELECT ReqId,[q] =''Q4_'' + CAST([year] AS CHAR(4)),quater4 FROM #forecast
)
SELECT *
FROM cte
PIVOT (MAX(quater) FOR q IN (<placeholder>)
) AS pvt;';
DECLARE @cols NVARCHAR(MAX) =
STUFF((SELECT ',' + QUOTENAME('Q1_' + CAST([year] AS CHAR(4))) +
',' + QUOTENAME('Q2_' + CAST([year] AS CHAR(4))) +
',' + QUOTENAME('Q3_' + CAST([year] AS CHAR(4))) +
',' + QUOTENAME('Q4_' + CAST([year] AS CHAR(4)))
FROM (SELECT DISTINCT [year] FROM #forecast) cte
ORDER BY [year]
FOR XML PATH(''), TYPE).value('.', 'NVARCHAR(MAX)') , 1, 1, '');
SET @sql = REPLACE(@sql, '<placeholder>', @cols);
EXEC [dbo].[sp_executesql] @sql;
的 LiveDemo3
强>
答案 1 :(得分:0)