[英]How does Oracle calculate the running total just by using order by clause?
[英]calculate running total with a date range in where clause using oracle sql
我有一个表,我想用 where 子句中的日期范围计算运行总计
+----------------+------------------+----------+
| Transaction ID | Transaction Date | Quantity |
+----------------+------------------+----------+
| 1 | 03-May-20 | 3 |
| 2 | 06-May-20 | 5 |
| 3 | 05-Jun-20 | 10 |
| 4 | 06-Jul-20 | 2 |
| 5 | 07-Aug-20 | 8 |
+----------------+------------------+----------+
现在我的 oracle sql 查询是
select
transaction_id,
transaction_date,
sum(quantity) over (order by transaction_date) as running_total
from table
where transaction_date >= '03-May-20' and transaction_date <= '06-Jul-20'
在我运行上面的查询之后,我得到了下面的结果
+----------------+------------------+----------+---------------+
| Transaction ID | Transaction Date | Quantity | Running Total |
+----------------+------------------+----------+---------------+
| 1 | 03-May-20 | 3 | 28 |
| 2 | 06-May-20 | 5 | 33 |
| 3 | 05-Jun-20 | 10 | 43 |
| 4 | 06-Jul-20 | 2 | 45 |
+----------------+------------------+----------+---------------+
这是错误的,因为我想要的 output 是:
| Transaction ID | Transaction Date | Quantity | Running Total |
+----------------+------------------+----------+---------------+
| 1 | 03-May-20 | 3 | 3 |
| 2 | 06-May-20 | 5 | 8 |
| 3 | 05-Jun-20 | 10 | 18 |
| 4 | 06-Jul-20 | 2 | 20 |
+----------------+------------------+----------+---------------+
请帮助我应该使用什么查询来计算带有 where 子句中的日期范围的运行总计。
嗨,我尝试使用 to_date function,但得到的结果与上面相同(第二张表)。 请参阅下面的查询,
select
transaction_id,
transaction_date,
sum(quantity) over (order by transaction_date) as running_total
from table
where transaction_date between TO_DATE('2019-03-01', 'YYYY-MM-DD') AND TO_DATE('2020-10-25', 'YYYY-MM-DD')
谢谢,
您想要的 Output(第 1 - 7 行中的示例数据;查询从第 8 行开始)。
SQL> with test (transaction_id, transaction_date, quantity) as
2 (select 1, date '2020-05-03', 3 from dual union all
3 select 2, date '2020-05-06', 5 from dual union all
4 select 3, date '2020-06-05', 10 from dual union all
5 select 4, date '2020-07-06', 2 from dual union all
6 select 5, date '2020-08-07', 8 from dual
7 )
8 select transaction_id,
9 transaction_date,
10 quantity,
11 sum(quantity) over (order by transaction_date) running_total
12 From test
13 where transaction_date between date '2020-05-03' and date '2020-07-06'
14 order by transaction_id;
TRANSACTION_ID TRANSACTIO QUANTITY RUNNING_TOTAL
-------------- ---------- ---------- -------------
1 03.05.2020 3 3
2 06.05.2020 5 8
3 05.06.2020 10 18
4 06.07.2020 2 20
SQL>
你的问题的原因? 我认为这是您将日期与字符串进行比较的事实( '03-May-20'
是一个字符串,而不是日期)。 Oracle 尝试隐式转换数据类型; 有时会成功,有时不会。 例如,您的03-May-20
可能是 2020 年 5 月 3 日或 2003 年 5 月 20 日。
始终控制您的数据。 必要时使用日期,通过使用带有适当日期格式掩码的to_date
,或使用日期文字(就像我所做的那样)。
您的查询是“正确的”,但您的结果不是,它们包含预期的运行总计,但它从最终总计(包括交易 ID 5)开始。 您运行了不同的 SQL 语句。
请注意,您不应将日期存储为字符串或将它们与字符串进行比较。 也就是说,如果您当前的 NLS 日期格式设置(很容易更改)与您的字符串输入匹配,Oracle 将节省您的培根。 如果您按字符串排序,您将得到完全不同的结果,您的结果具有预期的交易日期值,因此人们会假设此比较有效。 您仍然应该修复对日期的处理,但这不是这里的问题。
其他事情正在发生。 数据根据日期正确汇总,因此日期排序似乎不是问题。
总和从总和减去第一个值开始。 所以,结果看起来像这个查询的结果:
select transaction_id, transaction_date, quantity,
total_quantity + sum(quantity) over (order by transaction_date)as running_total
From (select t.*,
sum(quantity) over () - first_value(quantity) over (order by transaction_date) as total_quantity
from test t
) t
where transaction_date between date '2020-05-03' and date '2020-07-06'
order by transaction_date;
我无法解释为什么会这样。 它可能是 Oracle 中的错误。或者它可能是您提出问题时过度简化查询的结果。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.