Как найти диапазоны дат в записях с последовательными датами? - PullRequest
0 голосов
/ 15 марта 2011

У меня есть таблица с данными примерно так:

ID    StartDate    EndDate     EffectiveDate
--    ---------    -------     -------------
1     1/1/2009     12/31/2009    12/31/2009
1     7/1/2009     12/31/2009    7/1/2009
1     8/1/2009     12/31/2009    8/1/2009
2     1/1/2010     12/31/2010    12/31/2010
2     3/1/2010     12/31/2010    12/31/2010

Мне нужен запрос, который отформатирует его так:

ID    StartDate    EndDate     EffectiveDate
--    ---------    -------     -------------
1     1/1/2009     6/30/2009    null
1     7/1/2009     7/31/2009    7/1/2009
1     8/1/2009     12/31/2009   8/1/2009
2     1/1/2010     2/28/2010    null
2     3/1/2010     12/31/2010   12/31/2010
...

Это в основном похоже на временную шкалу с сегментированными «точками», и каждая точка - это новая StartDate с EndDate следующей точки и т. Д.

Я пытался использовать CTE, а также следующий запрос:

   SELECT t1.RfqItemOptionId, 
          t1.StartDate, 
          MIN(t2.EffectiveDate) EndDate,  
          t1.EffectiveDate EffectiveDate
     FROM @OptionPeriods t1 
LEFT JOIN @OptionPeriods t2 ON t1.RfqItemOptionId = t2.RfqItemOptionId
                           AND t1.EffectiveDate < t2.EffectiveDate
 GROUP BY t1.RfqItemOptionId, t1.StartDate, t1.EffectiveDate

Что близко ... но без сигары: (

Может кто-нибудь помочь?

Ответы [ 2 ]

3 голосов
/ 15 марта 2011
;With Base As
(
    Select
          *
        , ROW_NUMBER() Over (Partition By ID Order By StartDate) RowNum
    From
        @OptionPeriods
)
Select
      B1.*
    , IsNull(B2.StartDate - 1, B1.EndDate) As NewEndDate
    , Case B1.RowNum When 1 then Null Else B1.StartDate End As NewEffectiveDate
From
    Base B1
Left Join
    Base B2
On
    B1.ID = B2.ID
    AND
    B1.RowNum + 1 = B2.RowNum
0 голосов
/ 14 ноября 2013

Я человек-оракул, вот оракул-версия SQL .... Замените соответствующий аналитический SQL на эквивалентный SQL-сервер SQL ...

SELECT id, 
       startdate,
       enddate,
       case WHEN enddate < effectivedate THEN null ELSE effectivedate end AS effectivedate
FROM (
    SELECT id, 
           startdate,
           nvl2(next_startdate,(next_startdate-1),enddate) enddate,
           effectivedate
    FROM (
        SELECT a.*,
               lead(startdate,1) over (partition by id order by id,startdate) next_startdate
        FROM tblTest a
        ORDER BY 1,2
    )
);

Спасибо, Venkat

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...