从Oracle中的表中选择从max有效日期到2年为止的记录

问题描述

我有一个查询,该查询返回ID,effectiveDate和许多其他列。现在,我需要过滤此结果,以获取每个ID的最近生效日期之前长达2年的记录。

表中的数据类似于以下内容

ID |       EffectiveDate   | Col3 |     Col4 | ........
____________________________________________________________
1  |       2020-09-30      |
1  |       2019-09-30      |
1  |       2018-09-30      |
1  |       2018-03-31      |
1  |       2017-09-30      |
2  |       2019-03-31      |
2  |       2018-03-31      |
2  |       2017-03-31      |
3  |       2015-06-30      |
3  |       2015-03-31      |
3  |       2014-12-31      |
3  |       2012-06-30      |

我希望输出

ID |       EffectiveDate   | Col3      Col4 ........
____________________________________________________________
1  |       2020-09-30      |
1  |       2019-09-30      |
1  |       2018-09-30      |
2  |       2019-03-31      |
2  |       2018-03-31      |
2  |       2017-03-31      |
3  |       2015-06-30      |
3  |       2015-03-31      |
3  |       2014-12-31      |

我尝试了以下

select A.* from table A
inner join
(select ID,col3,col4,max(effectivedate) as MaxDate
from table A
group by ID,Col4 ) B
on A.ID = B.ID
where (B.Maxdate - A.effectiveDate) < 740;

,但是此查询返回所有记录,不过滤任何内容。这也会引发交叉联接结果。请帮忙!

解决方法

使用窗口功能。您的文本指定了每个id的最大值:

select a.*
from (select a.*,max(efectivedate) over (partition by id) as max_ed
      from a
     ) a
where effectivedate >= max_ed - interval '740' day;

(注意:730会更有意义。)

如果您希望根据查询的建议,以id / col3 / col4的身份使用partition by中的所有三个字符。

,

如果是“ 2年”,则将其设为2年而不是740天。

SQL> with test (id,efdate) as
  2    (select 1,date '2020-09-30' from dual union all
  3     select 1,date '2019-09-30' from dual union all
  4     select 1,date '2018-09-30' from dual union all
  5     select 1,date '2017-09-30' from dual union all
  6     select 2,date '2019-03-31' from dual union all
  7     select 2,date '2018-03-31' from dual union all
  8     select 2,date '2017-03-31' from dual
  9    ),10  tmp as
 11    (select id,efdate,max(efdate) over (partition by id) maxdate
 12     from test
 13    )
 14  select t.id,t.efdate
 15  from test t join tmp m on t.id = m.id and t.efdate = m.efdate
 16  where t.efdate >= add_months(m.maxdate,-12 * 2)
 17  order by t.id,t.efdate desc;

        ID EFDATE
---------- ----------
         1 2020-09-30
         1 2019-09-30
         1 2018-09-30
         2 2019-03-31
         2 2018-03-31
         2 2017-03-31

6 rows selected.

SQL>
,

这也应该起作用。所有条件都在WHERE子句中。它使用每个组ID的最大日期,并对每个记录进行减法,然后根据需要获得结果。

select * from tbl A
where (select max(B.effectivedate) from tbl B where A.id = B.id) - A.effectivedate < 740
order by A.id asc,A.effectivedate desc;