2016-07-17 106 views
0

我現在有一個查詢,其中列出了過去12個月灌裝每月銷售額的表在過去12個月SQL

SELECT 
    TOP 10 SUM(CustomerInvoice.Total) AS 'Total', CustomerName 
FROM dbo.CustomerInvoice 
INNER JOIN dbo.Customer 
    ON CustomerInvoice.BillToCode = Customer.CustomerCode 
WHERE InvoiceDate BETWEEN CAST(dateadd(year, -1, getdate()) AS SMALLDATETIME) AND CAST(GETDATE() AS SMALLDATETIME) 
    GROUP BY CustomerName 
    ORDER BY Total DESC 

這將返回一個表,像這樣和銷售。

╔═══════════╦═══════════════╗ 
║ Total  ║ Customer Name ║ 
╠═══════════╬═══════════════╣ 
║ 806405.85 ║ Customer 1 ║ 
╠═══════════╬═══════════════╣ 
║ 128244.77 ║ Customer 2 ║ 
╠═══════════╬═══════════════╣ 
║ 80127.75 ║ Customer 3 ║ 
╠═══════════╬═══════════════╣ 
║ 71994.56 ║ Customer 4 ║ 
╠═══════════╬═══════════════╣ 
║ 67641.31 ║ Customer 5 ║ 
╠═══════════╬═══════════════╣ 
║ 67064.04 ║ Customer 6 ║ 
╠═══════════╬═══════════════╣ 
║ 60324.39 ║ Customer 7 ║ 
╠═══════════╬═══════════════╣ 
║ 59684.7 ║ Customer 8 ║ 
╠═══════════╬═══════════════╣ 
║ 59066.31 ║ Customer 9 ║ 
╠═══════════╬═══════════════╣ 
║ 57112.04 ║ Customer 10 ║ 
╚═══════════╩═══════════════╝ 

我需要什麼是這些客戶的月銷量,以表格的形式是這樣的:

╔═══════════════╦═════════╦═════════╦═════════╦═════════╦═════════╦═════════╦═════════╦═════════╦═════════╦═════════╦═════════╦═════════╗ 
║ ///////////// ║ Jul-15 ║ Aug-15 ║ Sep-15 ║ Oct-15 ║ Nov-15 ║ Dec-15 ║ Jan-16 ║ Feb-16 ║ Mar-16 ║ Apr-16 ║ May-16 ║ Jun-16 ║ 
╠═══════════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╣ 
║ Customer 1 ║ 2087.23 ║ 4289.49 ║ 2326.14 ║ 1058.48 ║ 552.03 ║ 2438.16 ║ 7146.80 ║ 9305.66 ║ 8800.45 ║ 7199.57 ║ 1247.92 ║ 8977.39 ║ 
╠═══════════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╣ 
║ Customer 2 ║ 36.28 ║ 9327.53 ║ 2385.92 ║ 9372.04 ║ 2877.75 ║ 543.23 ║ 5464.15 ║ 4426.06 ║ 93.84 ║ 843.24 ║ 6895.55 ║ 74.02 ║ 
╠═══════════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╣ 
║ Customer 3 ║ 9492.12 ║ 9285.28 ║ 4528.11 ║ 7198.50 ║ 4037.02 ║ 5160.75 ║ 8246.33 ║ 6806.81 ║ 7051.14 ║ 814.43 ║ 9631.44 ║ 804.93 ║ 
╠═══════════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╣ 
║ Customer 4 ║ 9217.58 ║ 9147.28 ║ 2202.67 ║ 6432.05 ║ 2365.12 ║ 4973.94 ║ 5486.00 ║ 1793.43 ║ 1284.91 ║ 3671.67 ║ 751.11 ║ 5483.26 ║ 
╠═══════════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╣ 
║ Customer 5 ║ 3211.68 ║ 3329.07 ║ 2319.50 ║ 5077.95 ║ 8977.03 ║ 6813.39 ║ 4890.97 ║ 345.05 ║ 483.89 ║ 565.10 ║ 7760.01 ║ 6465.55 ║ 
╠═══════════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╣ 
║ Customer 6 ║ 1683.52 ║ 4287.37 ║ 524.30 ║ 4595.54 ║ 1102.11 ║ 4623.11 ║ 3165.83 ║ 2363.13 ║ 2584.55 ║ 3420.01 ║ 9496.31 ║ 2940.19 ║ 
╠═══════════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╣ 
║ Customer 7 ║ 1325.93 ║ 1847.88 ║ 3107.79 ║ 1855.39 ║ 7698.80 ║ 5360.15 ║ 7752.69 ║ 8289.06 ║ 8444.03 ║ 2719.06 ║ 6187.75 ║ 4921.10 ║ 
╠═══════════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╣ 
║ Customer 8 ║ 7573.35 ║ 2198.58 ║ 3432.29 ║ 6427.38 ║ 3856.54 ║ 9164.15 ║ 4945.19 ║ 9812.18 ║ 4712.47 ║ 5530.55 ║ 2396.45 ║ 2914.75 ║ 
╠═══════════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╣ 
║ Customer 9 ║ 8278.74 ║ 4865.93 ║ 4071.40 ║ 5628.76 ║ 3202.43 ║ 7270.84 ║ 811.55 ║ 275.52 ║ 3451.58 ║ 8164.47 ║ 8117.53 ║ 66.86 ║ 
╠═══════════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╬═════════╣ 
║ Customer 10 ║ 581.96 ║ 8288.06 ║ 521.93 ║ 8938.67 ║ 3211.10 ║ 348.94 ║ 6841.85 ║ 3282.51 ║ 2007.62 ║ 1621.19 ║ 5982.00 ║ 3841.82 ║ 
╚═══════════════╩═════════╩═════════╩═════════╩═════════╩═════════╩═════════╩═════════╩═════════╩═════════╩═════════╩═════════╩═════════╝ 

我有這個疑問,但有什麼辦法,我可以有查詢動態選擇過去12個月的列?

SELECT TOP 100 * FROM(
SELECT CustomerName 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2015 AND DATEPART(MONTH, InvoiceDate) = 8 THEN Total ELSE 0 END) AS [Aug-15] 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2015 AND DATEPART(MONTH, InvoiceDate) = 9 THEN Total ELSE 0 END) AS [Sep-15] 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2015 AND DATEPART(MONTH, InvoiceDate) = 10 THEN Total ELSE 0 END) AS [Oct-15] 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2015 AND DATEPART(MONTH, InvoiceDate) = 11 THEN Total ELSE 0 END) AS [Nov-15] 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2015 AND DATEPART(MONTH, InvoiceDate) = 12 THEN Total ELSE 0 END) AS [Dec-15] 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2016 AND DATEPART(MONTH, InvoiceDate) = 1 THEN Total ELSE 0 END) AS [Jan-16] 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2016 AND DATEPART(MONTH, InvoiceDate) = 2 THEN Total ELSE 0 END) AS [Feb-16] 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2016 AND DATEPART(MONTH, InvoiceDate) = 3 THEN Total ELSE 0 END) AS [Mar-16] 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2016 AND DATEPART(MONTH, InvoiceDate) = 4 THEN Total ELSE 0 END) AS [Apr-16] 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2016 AND DATEPART(MONTH, InvoiceDate) = 5 THEN Total ELSE 0 END) AS [May-16] 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2016 AND DATEPART(MONTH, InvoiceDate) = 6 THEN Total ELSE 0 END) AS [Jun-16] 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = 2016 AND DATEPART(MONTH, InvoiceDate) = 7 THEN Total ELSE 0 END) AS [Jul-16] 
, SUM(CASE WHEN InvoiceDate BETWEEN CAST(dateadd(year, -1, getdate()) AS SMALLDATETIME) AND CAST(GETDATE() AS SMALLDATETIME) THEN CI.Total ELSE 0 END) AS 'Total' 
FROM CustomerInvoice CI 
    JOIN Customer C ON CI.BillToCode = C.CustomerCode 
    GROUP BY C.CustomerName) A 
    ORDER BY Total DESC 
+0

pivoting或使用條件聚合將得到你想要的東西...但是如果它需要動態生成列名稱(例如在任何給定時間的最後12個月),它將需要使用動態SQL – ZLK

+0

Thanks @ ZLK。你可以通過動態SQL給我更多的信息,或者向我指出一些教程或者關於如何使用它的文檔?我正在使用SQL Server 2008 –

+0

請參閱這裏http://stackoverflow.com/questions/10404348/sql-server-dynamic-pivot-query – sqluser

回答

1

要生產的列名,創建一個變量,像這樣:

DECLARE @cols VARCHAR(4000) = ''; 
SELECT @cols += ' 
, SUM(CASE WHEN DATEPART(YEAR, InvoiceDate) = ' + CAST(DATEPART(YEAR, DATEADD(MONTH, -number, GETDATE())) AS CHAR(4)) + ' AND DATEPART(MONTH, InvoiceDate) = ' + CAST(DATEPART(MONTH, DATEADD(MONTH, -number, GETDATE())) AS CHAR(4)) + ' THEN Total ELSE 0 END) AS ' + QUOTENAME(LEFT(DATENAME(MONTH, DATEADD(MONTH, -number, GETDATE())), 3) + '-' + RIGHT(DATEPART(YEAR, DATEADD(MONTH, -number, GETDATE())), 2)) 
FROM master..spt_values 
WHERE number < 12 
AND type = 'p' 
ORDER BY number DESC; 
--PRINT @cols; 

在動態SQL中使用這是什麼做的是生產select語句的一部分。這是你的條件聚合。

然後你寫你的動態SQL並執行它,像這樣......

DECLARE @SQL NVARCHAR(MAX) = 'SELECT CustomerName' + @cols + ' 
FROM dbo.CustomerInvoice CI 
JOIN dbo.Customer C ON CI.BillToCode = C.CustomerCode 
WHERE InvoiceDate BETWEEN CAST(DATEADD(YEAR, -1, GETDATE()) AS SMALLDATETIME) AND CAST(GETDATE() AS SMALLDATETIME) 
AND CustomerName IN (
    SELECT TOP 10 CustomerName 
    FROM dbo.CustomerInvoice CI 
    JOIN dbo.Customer C ON CI.BillToCode = C.CustomerCode 
    WHERE InvoiceDate BETWEEN CAST(DATEADD(YEAR, -1, GETDATE()) AS SMALLDATETIME) AND CAST(GETDATE() AS SMALLDATETIME) 
    ORDER BY SUM(CI.Total) DESC) 
GROUP BY CustomerName 
ORDER BY SUM(CI.Total) DESC'; 
--PRINT @SQL; 

EXEC sp_executesql @SQL; 

本質上講,你需要知道的前10名顧客對於某一年(的報表會告訴你這),但你需要外部查詢來告訴日期細分。

+0

我收到'無效的對象名稱CustomerInvoice'錯誤。這是我的@SQL輸出 - https://codeshare.io/OLt1r –

+0

在您的第二個代碼塊的第二行的FROM CustomerInvoice CI之後出現錯誤 –

+0

@BrendanGooden我讀了模式(dbo),因爲這似乎就像它可能會導致錯誤一樣。 – ZLK

相關問題