查找逾期天数的 SQL 窗口函数
Posted
技术标签:
【中文标题】查找逾期天数的 SQL 窗口函数【英文标题】:SQL Window function to find days past due 【发布时间】:2020-04-19 21:22:48 【问题描述】:我想从按日期排序的贷款列表中计算 DPD(逾期天数)。每个过去的到期日都应重新计算。 参见附件中的示例。如何计算“逾期天数”列?
【问题讨论】:
请用您正在使用的数据库标记您的问题:mysql、oracle、postgresql...?此外,以表格文本而不是图像的形式提供数据会好得多。 请用您正在使用的数据库标记您的问题。 你想要的结果是什么?对于这笔贷款,DPD 是 4、6、0 还是其他? 【参考方案1】:应该这样做。
SELECT
t1.LoanNumber, t1.daydate, t1.Status, case
when status = 'Past Due'
then datediff(day,
(select max(daydate) from table1 t2
where t2.loanNumber =t1.loanNumber
and t2.daydate<t1.daydate and t2.status<> 'Past Due'
),
daydate)
else 0 end as [Days Past Due]
from table1 t1
你可以试试sqlfiddle
【讨论】:
【参考方案2】:出于某种原因,我将其视为 SQL Server。下面将 SQL Server 约定用于日期函数。其他数据库也有类似的功能,只是语法不同。
关键 ida - 一个累积条件最大值 - 不会改变:
select t.*,
(case when status = 'PastDue'
then datediff(date,
max(case when status <> 'PastDue' then dayDate end) over (partition by loadnumer order by daydate)
else 0
end) as daysPastDue
from t;
【讨论】:
【参考方案3】:您想要计算“逾期”的连续天数并在其间重置计数器。这是差距和孤岛问题。
如果日期总是增加 1 天,如您的示例数据所示,那么一种方法是取日期和 row_number()
之间的差值来定义每条记录所属的组。
你没有告诉你使用的是哪个数据库,所以这里有一个使用SQL Server的dateadd()
进行日期计算的方法;不支持但具有等效功能的数据库。
select
loan_number,
daydate,
status,
case when status = 'PastDue' then
count(*) over(
partition by loan_number, status, dateadd(day, -rn, daydate)
order by daydate
)
else 0
end daysPastDue
from (
select
t.*,
row_number() over(partition by loan_number, status order by daydate) rn
from mytable t
) t
order by loan_number, daydate
Demo on DB Fiddle:
贷款号码 |约会 |状态 | daysPastDue ----------: | :--------- | :------- | ----------: 111111 | 2020-01-01 |直播 | 0 111111 | 2020-01-02 |直播 | 0 111111 | 2020-01-03 |逾期 | 1 111111 | 2020-01-04 |逾期 | 2 111111 | 2020-01-05 |重组 | 0 111111 | 2020-01-06 |重组 | 0 111111 | 2020-01-07 |重组 | 0 111111 | 2020-01-08 |逾期 | 1 111111 | 2020-01-09 |逾期 | 2 111111 | 2020-01-10 |关闭 | 0【讨论】:
以上是关于查找逾期天数的 SQL 窗口函数的主要内容,如果未能解决你的问题,请参考以下文章
查找 SQL 聚合函数调用中的百分比可能没有嵌套聚合或窗口函数
如何使用天数作为 pandas rolling_apply 函数的窗口