PostgreSQL
 sql >> Baza danych >  >> RDS >> PostgreSQL

Uzyskaj całkowity przedział czasu z wielu wierszy, jeśli sekwencja nie jest zepsuta

Może istnieć sposób na zrobienie tego w jednym wyborze SQL, ale mi to umyka. Udało mi się to zrobić za pomocą jednej zapisanej funkcji. Oto, co zrobiłem podczas testów:

create table work
(id integer, start_date date, end_date date);

insert into work values (1, '2011-01-01','2011-02-02');
insert into work values (1, '2011-02-02','2011-04-04');
insert into work values (1, '2011-06-06','2011-09-09');
insert into work values (2, '2011-01-01','2011-02-02');
insert into work values (2, '2011-02-02','2011-03-03');

create or replace function get_data() returns setof work as
$body$
declare
    res work%rowtype;
    sd  date := null;
begin
    for res in
        select
            w1.id,
            case when exists (select 1 from work w2 where w1.id=w2.id and w2.end_date=w1.start_date) then null else w1.start_date end,
            case when exists (select 1 from work w2 where w1.id=w2.id and w2.start_date=w1.end_date) then null else w1.end_date end
        from
            work w1
        order by
            id, start_date, end_date
    loop
        if res.start_date is not null and res.end_date is not null then
            return next res;
        elsif res.start_date is not null then
            sd := res.start_date;
        elsif res.end_date is not null then
            res.start_date := sd;
            return next res;
        end if;
    end loop;

    return;
end;$body$
  language 'plpgsql';

Następnie

select * from get_data() order by id, start_date;

zwrócił ten wynik:

 id | start_date |  end_date
----+------------+------------
  1 | 2011-01-01 | 2011-04-04
  1 | 2011-06-06 | 2011-09-09
  2 | 2011-01-01 | 2011-03-03
(3 rows)

to jest, jak sądzę, to, czego szukasz.



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Zgłoś błąd, gdy data jest nieprawidłowa

  2. Opcjonalny argument w funkcji PL/pgSQL

  3. Tworzenie użytkownika PostgreSQL i dodawanie go do bazy danych

  4. Zadeklaruj zmienną typu wiersza w PL/pgSQL

  5. Dlaczego pg_restore zwraca pomyślnie, ale w rzeczywistości nie przywraca mojej bazy danych?