【问题标题】:SQL sub select if existsSQL子选择是否存在
【发布时间】:2013-03-14 07:34:51
【问题描述】:

我使用的是 SQL Server 2012。我有两个表来保存产品订单。具有接收日期的订单和具有价格和订单 ID fk 的 OrderItem。

我正在尝试编写一个查询,获取某个日期范围内的所有订单,按日期对它们进行分组,然后对所有订单商品的价格求和以获得该日期所有订单的总和。

我有这个工作。现在我想添加另一列来选择当天总价与 7 天前之间的差额。如果 7 天前没有订单,则该列应为空。

所以目前我有以下查询:

select cast(o.ReceivedDate as date) as OrderDate, 
coalesce(count(orderItems.orderId), 0) as Orders,
coalesce(sum(orderItems.Price), 0) as Price
from [Order] o

left outer join (
        select o.Id as orderId, sum(ot.Price) as Price
        from OrderItem ot
        join [Order] o on ot.OrderId = o.Id
        where o.ReceivedDate >= @DateFrom and o.ReceivedDate <= @DateTo
        group by o.Id
) as orderItems on o.Id = orderItems.orderId

where o.ReceivedDate >= @DateFrom and o.ReceivedDate <= @DateTo
group by cast(o.ReceivedDate as date)
order by cast(o.ReceivedDate as date) desc

那么如何将我的其他列添加到此查询中?我需要做类似的事情:

//pseudo 
if o.RecievedDate - 7 exists then orderItems.Price - Price from 7 days ago else null

但我不知道该怎么做?我创建了一个 sqlfiddle 来帮助解释 http://sqlfiddle.com/#!6/8b837/1

所以从我的示例数据中我想要达到的结果是这样的:

|  ORDERDATE | ORDERS | PRICE |  DIFF7DAYS  |
---------------------------------------------
| 2013-01-25 |      3 |    38 |          28 |
| 2013-01-24 |      1 |    12 |        null |
| 2013-01-23 |      1 |    10 |        null |
| 2013-01-22 |      1 |    33 |        null |
| 2013-01-18 |      1 |    10 |        null |
| 2013-01-10 |      1 |     3 |         -43 |
| 2013-01-08 |      2 |    11 |        null |
| 2013-01-04 |      1 |     1 |        null |
| 2013-01-03 |      3 |    46 |        null |

如您所见,25 日有 7 天前的订单,因此显示了差异。 24th 的显示不是那么空。

任何帮助将不胜感激。

【问题讨论】:

    标签: sql sql-server tsql sql-server-2012


    【解决方案1】:

    不知道您为什么在[Orders] 表和the subquery 之间使用left outer join,因为没有订单项(通常)就不能下订单:

    要获得您的结果,您可以使用CTE 进行如下简化版本

    SQL-FIDDLE-DEMO

    ;with cte as (
      select convert(date,o.ReceivedDate) orderDate,
           count(distinct o.Id) as Orders,
           coalesce(sum(ot.Price),0) as Price
      from OrderItem ot
            join [Order] o on ot.OrderId = o.Id
      where o.ReceivedDate >= @DateFrom and o.ReceivedDate <= @DateTo
      group by convert(date,o.ReceivedDate)
    )
    select c1.orderDate, c1.Orders, c1.Price, c1.Price-c2.Price DIFF7DAYS
    from cte c1 left join cte c2 on dateadd(day,-7,c1.orderdate) = c2.orderdate
    order by c1.orderdate desc
    
    
    |  ORDERDATE | ORDERS | PRICE | DIFF7DAYS |
    -------------------------------------------
    | 2013-01-25 |      3 |    38 |        28 |
    | 2013-01-24 |      1 |    12 |    (null) |
    | 2013-01-23 |      1 |    10 |    (null) |
    | 2013-01-22 |      1 |    33 |    (null) |
    | 2013-01-18 |      1 |    10 |    (null) |
    | 2013-01-10 |      1 |     3 |       -43 |
    | 2013-01-08 |      2 |    11 |    (null) |
    | 2013-01-04 |      1 |     1 |    (null) |
    | 2013-01-03 |      3 |    46 |    (null) |
    

    【讨论】:

      【解决方案2】:

      使用临时表并将其加入日期差异。

      DECLARE @DateFrom datetime
      SET @DateFrom = '2012-12-02'
      
      DECLARE @DateTo datetime
      SET @DateTo = '2013-03-13'
      
      CREATE TABLE #temp ( orderdate date, orders int, price money)
      INSERT INTO #temp
      SELECT cast(o.ReceivedDate AS date) AS OrderDate,
      coalesce(count(orderItems.orderId), 0) AS Orders,
      coalesce(sum(orderItems.Price), 0) AS Price
      FROM [Order] o
      
      LEFT OUTER JOIN (
      SELECT o.Id AS orderId, sum(ot.Price) AS Price
      FROM OrderItem ot
      JOIN [Order] o ON ot.OrderId = o.Id
      WHERE o.ReceivedDate >= @DateFrom AND o.ReceivedDate <= @DateTo
      GROUP BY o.Id
      ) AS orderItems ON o.Id = orderItems.orderId
      
      WHERE o.ReceivedDate >= @DateFrom AND o.ReceivedDate <= @DateTo
      GROUP BY cast(o.ReceivedDate AS date)
      
      SELECT t1.orderdate, t1.orders, t1.price, 
      t1.price - t2.price AS diff7days
      FROM #temp t1 LEFT JOIN #temp t2
      ON datediff(DAY, t2.orderdate, t1.orderdate) = 7
      ORDER BY t1.orderdate DESC
      

      http://sqlfiddle.com/#!6/8b837/34

      【讨论】:

        猜你喜欢
        • 2019-12-21
        • 2013-05-25
        • 1970-01-01
        • 1970-01-01
        • 2018-11-21
        • 1970-01-01
        • 2013-09-15
        • 2017-05-24
        • 1970-01-01
        相关资源
        最近更新 更多