2017-07-14 12 views
0

我有一個表foo與列id(不唯一),start_dateend_date。我想,對於具有某個id的所有行,沒有[start_date,end_date)範圍重疊。我想通過更改有問題的行的end_date來做到這一點。如何將範圍更新爲不重疊?

update foo old 
set end_date = new.start_date 
from foo new 
where old.start_date < new.start_date and old.end_date > new.start_date 
and old.id = new.id and new.id = 8675309; 

然而,這不會如果old重疊多個其他記錄工作。我的最佳嘗試是

update foo old 
set end_date = (select coalesce(min(new.start_date), old.end_date) 
    from foo new 
    where old.start_date < new.start_date and old.end_date > new.start_date 
    and new.id = old.id) 
where old.id = 8675309; 

這可行,但它不必要地更新每一行,感覺就像一個黑客。什麼是最好的方法來做到這一點?

回答

0

此假設start_date是內id

update foo 
set end_date = s.lsd 
from (
    select 
     id, start_date, 
     lead (start_date, 1, end_date) over (
      partition by id order by start_date 
     ) as lsd 
    from foo 
) s 
where 
    foo.id = s.id and 
    foo.start_date = s.start_date and 
    foo.end_date > s.lsd 
獨特