Given the following table
PAYMENT_Date TRANSACTION_TYPE PAYMENT_AMT
1/1/2012 P 184366
1/1/2012 R -5841
1/2/2012 P 941
1/3/2012 P 901
1/3/2012 R 5841
and the following query:
select payment_date, transaction_type, payment_amt,
SUM(payment_amt) OVER(ORDER BY payment_date, transaction_type
RANGE BETWEEN CURRENT ROW AND UNBOUNDED FOLLOWING) AS RUNNING_BALANCE
from TABLE;
I get these results:
PAYMENT_Date TRANSACTION_TYPE PAYMENT_AMT RUNNING_BALANCE
1/1/2012 P 184366 0
1/1/2012 R -5841 -184366
1/2/2012 P 941 -178525
1/3/2012 P 901 -179466
1/3/2012 R 5841 -180367
EXPECTED:
PAYMENT_Date TRANSACTION_TYPE PAYMENT_AMT RUNNING_BALANCE
1/1/2012 P 184366 0
1/1/2012 R -5841 184366
1/2/2012 P 941 178525
1/3/2012 P 901 179466
1/3/2012 R 5841 180367
Why does RUNNING_BALANCE come back as a negative number? How can I make it not, besides the obvious abs()?
First, the data and query you posted don't appear to generate the output you're seeing. So there is some sort of copy and paste error somewhere
SQL> with t as (
2 select date '2012-01-01' payment_date, 'P' transaction_type, 184366 payment_amt from dual union all
3 select date '2012-01-01', 'R', -5841 from dual union all
4 select date '2012-01-02', 'P', 941 from dual union all
5 select date '2012-01-03', 'P', 901 from dual union all
6 select date '2012-01-03', 'R', 5841 from dual
7 )
8 select payment_date, transaction_type, payment_amt,
9 SUM(payment_amt) OVER(ORDER BY payment_date, transaction_type
10 RANGE BETWEEN CURRENT ROW AND UNBOUNDED FOLLOWING) AS RUNNING_BALANCE
11 from T;
PAYMENT_D T PAYMENT_AMT RUNNING_BALANCE
--------- - ----------- ---------------
01-JAN-12 P 184366 186208
01-JAN-12 R -5841 1842
02-JAN-12 P 941 7683
03-JAN-12 P 901 6742
03-JAN-12 R 5841 5841
Normally, a running balance would be done just by omitting the RANGE BETWEEN clause.
SQL> ed
Wrote file afiedt.buf
1 with t as (
2 select date '2012-01-01' payment_date, 'P' transaction_type, 184366 payment_amt from dual union all
3 select date '2012-01-01', 'R', -5841 from dual union all
4 select date '2012-01-02', 'P', 941 from dual union all
5 select date '2012-01-03', 'P', 901 from dual union all
6 select date '2012-01-03', 'R', 5841 from dual
7 )
8 select payment_date, transaction_type, payment_amt,
9 SUM(payment_amt) OVER(ORDER BY payment_date, transaction_type) AS RUNNING_BALANCE
10* from T
SQL> /
PAYMENT_D T PAYMENT_AMT RUNNING_BALANCE
--------- - ----------- ---------------
01-JAN-12 P 184366 184366
01-JAN-12 R -5841 178525
02-JAN-12 P 941 179466
03-JAN-12 P 901 180367
03-JAN-12 R 5841 186208
In your case, though, it sounds like you want the running balance to exclude the current row's payment. That's a bit odd buy you can do it by adding an additional LAG
SQL> ed
Wrote file afiedt.buf
1 with t as (
2 select date '2012-01-01' payment_date, 'P' transaction_type, 184366 payment_amt from dual union all
3 select date '2012-01-01', 'R', -5841 from dual union all
4 select date '2012-01-02', 'P', 941 from dual union all
5 select date '2012-01-03', 'P', 901 from dual union all
6 select date '2012-01-03', 'R', 5841 from dual
7 )
8 select payment_date,
9 transaction_type,
10 payment_amt,
11 NVL( LAG(running_balance) OVER(ORDER BY payment_date,
12 transaction_type), 0) new_running_balance
13 from (select payment_date,
14 transaction_type,
15 payment_amt,
16 SUM(payment_amt) OVER(ORDER BY payment_date,
17 transaction_type) AS RUNNING_BALANCE
18* from t)
SQL> /
PAYMENT_D T PAYMENT_AMT NEW_RUNNING_BALANCE
--------- - ----------- -------------------
01-JAN-12 P 184366 0
01-JAN-12 R -5841 184366
02-JAN-12 P 941 178525
03-JAN-12 P 901 179466
03-JAN-12 R 5841 180367
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With