SQL Server聚合日期范围

时间:2016-07-29 11:43:30

标签: sql sql-server-2014 aggregates

我正在使用SQL Server 2014.我需要在按客户和位置分区或分组的日期范围内汇总总计(总计)。关键是获取所有调整金额,并在它们应用于开票交易日期时总结。

因此,在最后一个账单日期之后的所有调整,但是小于下一个账单日期需要总结并与账单金额一起很好地呈现。

参见示例:

+------------------+------------+------------+------------------+--------------------+
| TRANSACTION_TYPE | CUSTOMERID | LOCATIONID | TRANSACTION DATE | TRANSACTION AMOUNT |
+------------------+------------+------------+------------------+--------------------+
| bill             | 215        | 102        | 7/7/2016         | $100.00            |
| bill             | 215        | 102        | 6/6/2016         | $121.00            |
| adj              | 215        | 102        | 6/1/2016         | $22.00             |
| adj              | 215        | 102        | 5/8/2016         | $0.35              |
| adj              | 215        | 102        | 5/7/2016         | $5.00              |
| bill             | 215        | 102        | 5/6/2016         | $115.00            |
| bill             | 215        | 102        | 4/7/2016         | $200.00            |
| adj              | 215        | 102        | 4/2/2016         | $4.35              |
| adj              | 215        | 102        | 4/1/2016         | $(0.50)            |
| adj              | 215        | 102        | 3/28/2016        | $33.00             |
| bill             | 215        | 102        | 3/28/2016        | $75.00             |
| adj              | 215        | 102        | 3/5/2016         | $0.33              |
| bill             | 215        | 102        | 3/3/2016         | $99.00             |
+------------------+------------+------------+------------------+--------------------+

我希望看到以下内容:

    +------------------+------------+------------+------------------+-------------+-------------------+
| TRANSACTION_TYPE | CUSTOMERID | LOCATIONID | TRANSACTION DATE | BILL AMOUNT | ADJUSTMENT AMOUNT |
+------------------+------------+------------+------------------+-------------+-------------------+
| bill             | 215        | 102        | 7/7/2016         | $100.00     | $-                |
| bill             | 215        | 102        | 6/6/2016         | $121.00     | $27.35            |
| bill             | 215        | 102        | 5/6/2016         | $115.00     | $-                |
| bill             | 215        | 102        | 4/7/2016         | $200.00     | $36.85            |
| bill             | 215        | 102        | 3/28/2016        | $75.00      | $0.33             |
| bill             | 215        | 102        | 3/3/2016         | $99.00      | $-                |
+------------------+------------+------------+------------------+-------------+-------------------+

2 个答案:

答案 0 :(得分:0)

你需要:

  • 首先将该表视为TransactionType上的两个(虚拟)子表;
  • 然后使用LEAD功能获取要应用的日期调整范围;和
  • 最后进行了一次eft加入。

下面的未经测试的SQL:

with
BillData as (
    select
        TransactionType,
        CustomerID,
        LocationID,
        TransactionDate,
        TransactionAmount,
        lead(TransactionDate, 1) over (partition by CustomerID 
                                       order by TransactionDate) as NextDate
    from @data bill
    where TransactionType = 'bill'
),
AdjData as (
    select
        CustomerID,
        TransactionDate,
        sum(TransactionAmount) as AdjAmount
    from @data adj
    where TransactionType = 'adj'
)
select
    bill.TransactionType,
    bill.CustomerID,
    bill.LocationID,
    bill.TransactionDate,
    sum(TransactionAmount)  as BillAmount,
    sum(AdjAmount)          as AdjAmount
from BillData bill
left join AdjData adj
    on adj.CustomerID = bill.CustomerID
   and bill.TransactionDate <= adj.TransactionDate
   and adj.TransactionDate < bill.NextDate
group by
    bill.TransactionType,
    bill.CustomerID,
    bill.LocationID,
    bill.TransactionDate
;

答案 1 :(得分:0)

这就是我最终做的事情:

        select
        bill.TransactionType,
        bill.CustomerID,
        bill.LocationID,
        bill.TransactionDate,
        TransactionAmount  as BillAmount,
        sum(AdjAmount)          as AdjAmount
    from 
    (
        select
            TransactionType,
            CustomerID,
            LocationID,
            TransactionDate,
            TransactionAmount,
            lag(TransactionDate, 1) over (partition by CustomerID, LocationID
                                           order by TransactionDate) as PreviousDate --NextDate
        from test1
        where TransactionType = 'bill'
    ) as bill
    left join
    (
        select
            CustomerID,
            LocationID,
            TransactionDate,
            TransactionAmount as AdjAmount
        from test1
        where TransactionType = 'adj'
    ) as adj
    ON 
        adj.CustomerID = bill.CustomerID
        and adj.LocationID = bill.LocationID
    and adj.TransactionDate >= bill.PreviousDate
    and adj.TransactionDate < bill.TransactionDate
    group by
        bill.TransactionType,
        bill.CustomerID,
        bill.LocationID,
        bill.TransactionDate,
        bill.TransactionAmount
    order by 4 desc