SQL Calculate Среднее время между первым и вторым порядком? (Вычисления sql основаны на min и min + 1?) - PullRequest
1 голос
/ 09 июля 2019

У меня есть простая таблица, которая содержит электронную почту клиента, количество его заказов (так, если это их 1-й, 3-й, 5-й и т. Д.), Дату создания этого заказа, стоимость этого заказа и общую сумму заказа. рассчитывать на этого клиента.

Вот как выглядит мой стол

Email          Order# Date     Value TotalOrders
r2n1w@gmail.com 1   12/1/2016   85  5
r2n1w@gmail.com 2   2/6/2017    125 5
r2n1w@gmail.com 3   2/17/2017   75  5
r2n1w@gmail.com 4   3/2/2017    65  5
r2n1w@gmail.com 5   3/20/2017   130 5
ation@gmail.com 1   2/12/2018   150 1
ylove@gmail.com 1   6/15/2018   36  3
ylove@gmail.com 2   7/16/2018   41  3
ylove@gmail.com 3   1/21/2019   140 3
keria@gmail.com 1   8/10/2018   54  2
keria@gmail.com 2   11/16/2018  65  2

Сначала я вычислил среднее время между всеми заказами, взяв данные минимального заказа и дату максимального заказа, и рассчитав среднее между ними, используя количество заказов.

Вот как я это сделал (с помощью некоторых пользователей SO):

select email,
       datediff(day,  min(Date), max(Date)) / nullif(total-1, 0) as AvgDays
from Table
group by email;

Это дает мне среднее значение между днями покупки на одного клиента. Затем я присоединился к этой таблице как подзапрос к исходной таблице и просто присоединился к ней по электронной почте клиента.

Теперь, что я хочу, это для каждого клиента, дни, которые потребовались, чтобы получить от первого заказа до второго (0 или ноль, если нет второго заказа), и дни, которые потребовались, чтобы добраться от второго заказа к третьему. (также, если нет третьего порядка)

Так что это будет в значительной степени точно так же, как мой верхний запрос, но вместо выполнения datediff для min и max, это будет datediff для min и min плюс 1. Или min плюс 1 и min плюс 2. И так далее.

Возможно ли это?

Или я мог бы сделать это, выполнив несколько операторов case, где Order # = 2 ..

Кроме того, мне не нужно это рекурсивно, если это слишком сложно, достаточно только первых трех заказов.

1 Ответ

1 голос
/ 09 июля 2019

Вы можете сделать это, используя условное агрегирование:

select email,
       datediff(day, min(Date), max(Date)) / nullif(total-1, 0) as AvgDays,
       datediff(day,
                 max(case when seqnum = 1 then date end),
                 max(case when seqnum = 2 then date end)
                ) as days_1_to_2,
       datediff(day,
                 max(case when seqnum = 2 then date end),
                 max(case when seqnum = 3 then date end)
                ) as days_2_to_3
from (select t.*,
             row_number() over (partition by email order by date) as seqnum
      from Table t
     ) t
group by email;
...