4 回答

TA貢獻1859條經驗 獲得超6個贊
如果您使用的是SQL Server 2005+,則可以使用該PIVOT
函數將數據從行轉換為列。
聽起來你需要使用動態sql如果周未知,但最初使用硬編碼版本更容易看到正確的代碼。
首先,這里有一些快速表定義和使用數據:
CREATE TABLE #yt ( [Store] int, [Week] int, [xCount] int);INSERT INTO #yt( [Store], [Week], [xCount])VALUES (102, 1, 96), (101, 1, 138), (105, 1, 37), (109, 1, 59), (101, 2, 282), (102, 2, 212), (105, 2, 78), (109, 2, 97), (105, 3, 60), (102, 3, 123), (101, 3, 220), (109, 3, 87);
如果您的值已知,那么您將對查詢進行硬編碼:
select *from ( select store, week, xCount from yt) srcpivot( sum(xcount) for week in ([1], [2], [3])) piv;
請參閱SQL Demo
然后,如果您需要動態生成周數,您的代碼將是:
DECLARE @cols AS NVARCHAR(MAX), @query AS NVARCHAR(MAX)select @cols = STUFF((SELECT ',' + QUOTENAME(Week) from yt group by Week order by Week FOR XML PATH(''), TYPE ).value('.', 'NVARCHAR(MAX)') ,1,1,'')set @query = 'SELECT store,' + @cols + ' from ( select store, week, xCount from yt ) x pivot ( sum(xCount) for week in (' + @cols + ') ) p 'execute(@query);
請參閱SQL Demo。
動態版本,生成week
應轉換為列的數字列表。兩者都給出相同的結果:
| STORE | 1 | 2 | 3 |
---------------------------
| 101 | 138 | 282 | 220 |
| 102 | 96 | 212 | 123 |
| 105 | 37 | 78 | 60 |
| 109 | 59 | 97 | 87 |

TA貢獻1773條經驗 獲得超3個贊
我之前通過使用子查詢實現了同樣的目標。因此,如果您的原始表名為StoreCountsByWeek,并且您有一個單獨的表列出了商店ID,那么它將如下所示:
SELECT StoreID,
Week1=(SELECT ISNULL(SUM(xCount),0) FROM StoreCountsByWeek WHERE StoreCountsByWeek.StoreID=Store.StoreID AND Week=1),
Week2=(SELECT ISNULL(SUM(xCount),0) FROM StoreCountsByWeek WHERE StoreCountsByWeek.StoreID=Store.StoreID AND Week=2),
Week3=(SELECT ISNULL(SUM(xCount),0) FROM StoreCountsByWeek WHERE StoreCountsByWeek.StoreID=Store.StoreID AND Week=3)
FROM Store
ORDER BY StoreID
這種方法的一個優點是語法更清晰,并且可以更容易地連接到其他表以將其他字段拉入結果中。
我的軼事結果是,在不到一秒的時間內完成了幾千行的查詢,我實際上有7個子查詢。但正如評論中所指出的那樣,以這種方式執行它的計算成本更高,因此如果您希望它在大量數據上運行,請小心使用此方法。
添加回答
舉報