单个查询中的JOIN,GROUP BY和SUM

时间:2013-11-28 15:00:56

标签: sql sql-server

发票表

 invoice_id    invoice_date
------------  --------------
     1          2013-11-27
     2          2013-10-09
     3          2013-09-12

订单表

order_id    invoice_id  product     quantity    total
---------   ----------  ---------   ---------   -------
   1            1       Product 1      100       1000
   2            1       Product 2      50        200
   3            2       Product 1      40        400
   4            3       Product 2      50        200

我想要一个产生以下结果的单个SQL查询

products    Month 9 Total   Month 10 Total   Mont 11 Total
--------    -------------   --------------   -------------
Product 1         0              400              100    
Product 2        200              0               200

我尝试了以下sql查询

SELECT orders.products, DATEPART(Year, invoices.invoice_date) Year, DATEPART(Month, invoices.invoice_date) Month, SUM(orders.total) [Total],
FROM invoices INNER JOIN orders ON invoices.invoice_id=orders.invoice_id
GROUP BY orders.products, DATEPART(Year, invoices.invoice_date), DATEPART(Month, invoices.invoice_date)

但它什么也没有回报。是否可以通过单个查询获得此结果,我应该为此做些什么?感谢

3 个答案:

答案 0 :(得分:2)

我想你想在这里使用PIVOT ......

试试这个:

WITH tmp
AS 
(
SELECT orders.products, 
       DATEPART(Year, invoices.invoice_date) Year, 
       DATEPART(Month, invoices.invoice_date) Month, 
       SUM(orders.total) [Total]
FROM invoices INNER JOIN orders ON invoices.invoice_id = orders.invoice_id
GROUP BY 
        orders.products, 
        DATEPART(Year, invoices.invoice_date), 
        DATEPART(Month, invoices.invoice_date)
)
SELECT products, 
       ISNULL([9],0) AS Nine, ISNULL([10],0) AS Ten, ISNULL([11],0) as Eleven
FROM tmp
PIVOT
(
   SUM([Total])
   FOR Month IN
   ( [9], [10], [11])
) as PVT;

您可以在此处进行修改:http://sqlfiddle.com/#!6/6f80f/6

答案 1 :(得分:0)

一种方法是使用案例:

Select 
    O.product,
    Sum(Case
        When DATEPART(M, I.invoice_Date) = 9 Then O.total
        Else 0
    End) as Month9,
    Sum(Case
        When DATEPART(M, I.invoice_Date) = 10 Then O.total
        Else 0
    End) as Month10,
    Sum(Case
        When DATEPART(M, I.invoice_Date) = 11 Then O.total
        Else 0
    End) as Month11
From Invoice I
    Left join Orders O on I.invoice_id = O.invoice_id
Group by O.product

使用Pivots还有另一种方法(取决于您的SQL版本)。

Select product, [9], [10], [11]
From 
(
    Select O.Product, O.total, DatePart(M, I.Invoice_Date) as [MonthNum]
    From Invoice I
        Left join Orders O on I.invoice_id = O.invoice_id
) P
PIVOT
(
    Sum(P.total)
    For [MonthNum] in ([9], [10], [11])
) as O

答案 2 :(得分:0)

你最好使用pivot。请记住,您必须在pivot..for..in子句中明确列出每个月。

select 
    *
into #invoices
from (
    select 1 as invoice_id, '2013-11-27' as invoice_date union all
    select 2,'2013-10-09' union all
    select 3,'2013-09-12' 
) x


select 
    *
into #orders
from (
    select 1 as order_id,1 as invoice_id,'Product 1' as product,100 as quantity,1000 as total union all
    select 2,1,'Product 2',50,200 union all
    select 3,2,'Product 1',40,400 union all
    select 4,3,'Product 2',50,200
) x

GO


select 
    Product, 
    [9], [10], [11]
from (
    select 
        o.product, datepart([month],i.invoice_date) as mon,
        o.total
    from #invoices i
    join #orders o
        on i.invoice_id=o.invoice_id
) x
pivot (
    sum(total) for mon in ([9],[10],[11])
) p