您如何找到在SQL Server 2014中具有多个帐户的客户的真实开始结束日期

问题描述 投票:2回答:2

我有一个支票帐户表,其中包含列Cust_id(客户ID),Open_Date(开始日期)和Closed_Date(结束日期)。每个帐户有一行。客户可以在任何给定时间开设多个帐户。我想知道此人成为客户已有多长时间了。eg1:

    CREATE TABLE [Cust](
        [Cust_id] [varchar](10) NULL,
        [Open_Date] [date] NULL,
        [Closed_Date] [date] NULL
)

insert into [Cust] values ('a123','10/01/2019','10/15/2019')
insert into [Cust] values ('a123','10/12/2019','11/01/2019')

理想情况下,我想将此表插入只有一行的表中,即该人从10/01/2019到11/01/2019一直是客户。 (在他关闭前一个帐户之前,他打开了第二个帐户。

类似,例如2:

insert into [Cust] values ('b245','07/01/2019','09/15/2019')
insert into [Cust] values ('b245','10/12/2019','12/01/2019')

在这种情况下,我希望看到两行-表明他是从07/01到09/15的客户,然后又是从10/12到12/01的客户。

您能指出我最佳方法吗?

sql sql-server tsql sql-server-2014 gaps-and-islands
2个回答
1
投票

我将其视为差距和孤岛问题。您想将周期重叠的相邻行分组在一起。

这是使用lag()和累积值sum()求解的一种方法。每当打开日期大于上一个记录的关闭日期时,就会开始一个新组。

select 
    cust_id,
    min(open_date) open_date,
    max(closed_date) closed_date
from (
    select 
        t.*,
        sum(case when not open_date <= lag_closed_date then 1 else 0 end) 
            over(partition by cust_id order by open_date) grp
    from (
        select 
            t.*,
            lag(closed_date) over (partition by cust_id order by open_date) lag_closed_date
        from cust t
    ) t
) t
group by cust_id, grp

[this db fiddle中使用您的示例数据,查询将产生:

cust_id |开放日期|截止日期:------ | :--------- | :----------a123 | 2019-10-01 | 2019-11-01b245 | 2019-07-01 | 2019-09-15b245 | 2019-10-12 | 2019-12-01

0
投票

您可以尝试类似的方法:

select distinct
  cust_id,
  (select min(Open_Date)
   from Cust as b
   where b.cust_id = a.cust_id and 
   a.Open_Date <= b.Closed_Date and
   a.Closed_Date >= b.Open_Date
  ),
  (select max(Closed_Date)
   from Cust as b
   where b.cust_id = a.cust_id and 
   a.Open_Date <= b.Closed_Date and
   a.Closed_Date >= b.Open_Date
  )
from Cust as a

因此,对于每一行-您正在从所有重叠范围中选择最小和最大日期,以后会分别过滤掉重复项

© www.soinside.com 2019 - 2024. All rights reserved.