Присоединяйтесь на Range в Postgres - PullRequest
0 голосов
/ 27 февраля 2020

У меня есть PostgreSQL таблица базы данных, подобная этой:

ID | Meal            |Person
--------------------------------
1  | Early Beakfast  | Abc
2  | Breakfast       | Abc
3  | Lunch           | Abc
4  | Afternoon Snack | Abc
5  | Evening Snack   | Abc
7  | Dinner          | Abc
8  | late Night Snack| Abc
9  | Afternoon Snack | Def
10 | Evening Snack   | Def

Я хочу вывод, подобный этому:

Anchor          | Before          | After            | Person
----------------------------------------------------------------
Afternoon Snack | Early Breakfast | Evening Snack    | Abc
Afternoon Snack | Breakfast       | Dinner           | Abc
Afternoon Snack | Lunch           | Late Night Snack | Abc
Afternoon Snack | NULL            | Evening Snack    | Def

Каков наилучший подход для получения этого результата?

Я пытался использовать самостоятельное соединение для ID IN (ID + 1, ID + 2, ... ID + N), но это невозможно. ПРИМЕЧАНИЕ. Это просто пример данных. Фактические данные содержат более 2 миллионов записей. Тем не менее, якорь остается прежним.

1 Ответ

0 голосов
/ 27 февраля 2020

Создание групп на основе количества полдников (совокупная сумма) и затем агрегирование:

select 'Afternoon Snack',
       max(case when seqnum = 0 then meal end) as before,
       max(case when seqnum = 1 then meal end) as after
from (select t.*,
             row_number() over (partition by person, grp, (meal <> 'Afternoon Snack') order by id) as seqnum
      from (select t.*,
                   count(*) filter (where meal = 'Afternoon Snack') over (partition by person order by id) as grp
            from t
           ) t
     ) t
where grp in (0, 1)
group by person, seqnum
order by person, seqnum;
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...