来自交易的账户报表 SQL

Statement of account from transactions SQL

我在 table 中有一个用户的交易列表,其中记录了 UserID、DateTime、TransactionType 和 Value。 TransactionID 是主键自动递增 1。TransactionType 定义了存款 (1) 或取款 (2),因此 table 中的所有值都是正数。我正在尝试创建总计 运行 的账户报表。

TransactionID    UserID    DateTime           TransactionTypeID    Value
     1            3112     01-04-2016 12:00          1              5.00
     3            3112     01-04-2016 13:00          2              2.00
     5            3112     01-04-2016 13:25          2              1.00
     8            3112     02-04-2016 12:00          1              10.00
     9            3112     02-04-2016 12:35          2              4.00

基本上我想创建一个 运行 帐户查询语句,其中要创建的总值为:

DateTime           TransactionTypeID    Deposit    Withdrawal    Balance
01-04-2016 12:00          1              5.00                     5.00
01-04-2016 13:00          2                          2.00         3.00
01-04-2016 13:25          2                          1.00         2.00
02-04-2016 12:00          1              10.00                   12.00
02-04-2016 12:35          2                          4.00         8.00

我已经尝试使用 OUTER APPLY 到 select 之前的交易,但在单个查询中没有成功。如有任何帮助,我们将不胜感激

SELECT 
    [UserID], [DateTime], 
    T.[Value] * 
    (CASE 
        WHEN [TransactionTypeID] IN (1, -- deposit
                                     2 -- withdrawal
                                    )
            THEN -1
            ELSE 1
     END),
    T2.Value AS PrevValue
FROM 
    [Transaction] T
OUTER APPLY 
    (SELECT TOP 1 T2.[Value]
     FROM [Transaction] T2
     WHERE UserID = 3112 
       AND T2.[TransactionID] > T.TransactionID
    ORDER BY T2.TransactionID) AS T2
WHERE 
    T.[UserID] = 3112
ORDER BY 
    T.[TransactionID] DESC

我找到了 SQL Server 2012 解决方案。如果您是 运行 旧版本,请检查备选方案。

它使用 SUM OVER..

select [TransactionID],
[DateTime],
( CASE WHEN [TransactionTypeID] IN (
                                1, -- deposits
                                2 -- withdrawals
                              )
                     THEN -[Value]
                     ELSE [Value]
                     END


                ),
       sum(( CASE WHEN [TransactionTypeID] IN (
                                1, -- deposits
                                2 -- withdrawals
                              )
                     THEN -[Value]
                     ELSE [Value]
                     END


                )) over(order by [DateTime] rows unbounded preceding) as runningtotal
from [Transaction]
WHERE UserID = 3112

您要求的查询应如下所示..

SQL 2005

SELECT  [DateTime],
        [TransactionID],
        [Deposit]    = CASE WHEN TransactionTypeID = 1 THEN [Value] END,
        [Withdrawal] = CASE WHEN TransactionTypeID = 2 THEN -[Value] END,
        [Balance]    = CASE TransactionTypeID WHEN 1 THEN [Value] 
                                              WHEN 2 THEN -[Value] END + ISNULL([PrevValue], 0)
FROM    [Transaction] t1
        OUTER APPLY (SELECT SUM(CASE TransactionTypeID WHEN 1 THEN [Value] 
                                                       WHEN 2 THEN -[Value] END) AS [PrevValue]
                        FROM [Transaction] t2 
                        WHERE t1.UserID = t2.UserID AND t2.[DateTime] < t1.[DateTime]) ca  
WHERE   UserID = 3112

SQL 2008+

SELECT  [DateTime],
        [TransactionID],
        [Deposit]    = CASE WHEN TransactionTypeID = 1 THEN [Value] END,
        [Withdrawal] = CASE WHEN TransactionTypeID = 2 THEN -[Value] END,
        [Balance]    = SUM(CASE TransactionTypeID WHEN 1 THEN [Value] 
                                                  WHEN 2 THEN -[Value] END) 
                            OVER (ORDER BY [DateTime])
FROM    [Transaction]
WHERE   UserID = 3112