объединить и сгруппировать таблицу a строк по таблице b даты - PullRequest
0 голосов
/ 19 января 2019

У меня есть две m:m таблицы, profile_wordcards и profile_activities.Я хочу сгруппировать все карточные карточки по датам создания деятельности, где profile_id = 2.

Т.е., если activity 1 было создано на 2019-01-19 2:12:05, любая карточная открытка, созданная в эту дату или раньше, должна быть сгруппирована по activity 1.Если activity 2 было создано в 2019-01-19 2:14:22, все карточные открытки, созданные в эту дату или ранее, должны быть сгруппированы по activity 2 и т. Д.

Таблица: profile_activities

activity_id | profile_id | created_at
------------------------------------------
1              2            2019-01-19 2:12:05
2              2            2019-01-19 2:14:22

Таблица: profile_wordcards

wordcard_id | profile_id | created_at   
-----------------------------------------   
386         2             2019-01-19 2:04:07    >> Everything below: less than activity 1 created at    
385         2             2019-01-19 2:05:19        
263         2             2019-01-19 2:05:19        
234         2             2019-01-19 2:11:49        
175         2             2019-01-19 2:12:02        
201         2             2019-01-19 2:12:02        
226         2             2019-01-19 2:12:04        
409         2             2019-01-19 2:12:05        
361         2             2019-01-19 2:12:05        
359         2             2019-01-19 2:12:25    >> Everything below: less than activity 2 created at    
188         2             2019-01-19 2:12:34        
227         2             2019-01-19 2:12:59        
187         2             2019-01-19 2:13:01        
228         2             2019-01-19 2:13:18        
384         2             2019-01-19 2:13:37        
177         2             2019-01-19 2:14:00        
225         2             2019-01-19 2:14:00        

Желаемый вывод:

wordcard_id | profile_id |  created_at     | activity_id | activity_created_at
--------------------------------------------------------------------------------------- 
-- GROUP 1 (ACTIVITY ID 1, any wordcard.created_at <= 2019-01-19 2:12:05)
-- >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
386             2       2019-01-19 2:04:07     1           2019-01-19 2:12:05
385             2       2019-01-19 2:05:19     1           2019-01-19 2:12:05
263             2       2019-01-19 2:05:19     1           2019-01-19 2:12:05
234             2       2019-01-19 2:11:49     1           2019-01-19 2:12:05
175             2       2019-01-19 2:12:02     1           2019-01-19 2:12:05
201             2       2019-01-19 2:12:02     1           2019-01-19 2:12:05
226             2       2019-01-19 2:12:04     1           2019-01-19 2:12:05
409             2       2019-01-19 2:12:05     1           2019-01-19 2:12:05
361             2       2019-01-19 2:12:05     1           2019-01-19 2:12:05
-- GROUP 2 (ACTIVITY ID 2, any wordcard.created_at <= 2019-01-19 2:14:22 but > 2019-01-19 2:12:05) 
-- >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>
359             2       2019-01-19 2:12:25     2           2019-01-19 2:14:22
188             2       2019-01-19 2:12:34     2           2019-01-19 2:14:22
227             2       2019-01-19 2:12:59     2           2019-01-19 2:14:22
187             2       2019-01-19 2:13:01     2           2019-01-19 2:14:22
228             2       2019-01-19 2:13:18     2           2019-01-19 2:14:22
384             2       2019-01-19 2:13:37     2           2019-01-19 2:14:22
177             2       2019-01-19 2:14:00     2           2019-01-19 2:14:22
225             2       2019-01-19 2:14:00     2           2019-01-19 2:14:22

Я пробовал:

select pwc.wordcard_id, pwc.created_at, pa.activity_id, pa.created_at, pwc.profile_id
from profile_wordcards pwc
left join profile_activities pa on (pa.created_at < pwc.created_at)
where pwc.profile_id = 2
order by activity_id asc

Но это возвращает а) идентификаторы активности, не привязанные к профилю 2, и б) не группируют, как ожидалось.

1 Ответ

0 голосов
/ 19 января 2019

Вместо присоединения profile_activities напрямую присоединяйтесь к подзапросу, который выбирает все столбцы из profile_activities, а также lag() ed created_at. Затем вы можете сравнить с created_at «предыдущего» действия. В качестве значения по умолчанию для lag(), которое берется при отсутствии предыдущей активности, используйте '-infinity'. Поскольку все метки времени больше отрицательной бесконечности, сравнение с карточкой слова created_at будет работать и в этих случаях.

SELECT w.wordcard_id,
       w.profile_id,
       w.created_at,
       a.activity_id,
       a.profile_id,
       a.created_at
       FROM (SELECT a.activity_id,
                    a.profile_id,
                    a.created_at,
                    lag(a.created_at,
                        1,
                        '-infinity') OVER (ORDER BY a.created_at) created_at_lag
                    FROM profile_activities a) a
            INNER JOIN profile_wordcards w
                       ON w.profile_id = a.profile_id
                          AND w.created_at > a.created_at_lag
                          AND w.created_at <= a.created_at
       ORDER BY a.activity_id;

дб <> скрипка

...