Как найти и сгруппировать временные цепочки за 36 секунд?

0
  • У меня есть таблица дат.
  • Я хочу найти и сгруппировать даты с разницей в 36 секунд.
  • есть ли разница в 36 секунд между предыдущей датой и следующей датой?
  • Если это так, это будет группа до конца цепи.
  • Если 36-секундная цепочка сломана, она начинает новую группу.
  • если нет цепочки в течение 36 секунд, значения finisDate и dateRangeID возвращают значение null

Я могу сделать это с помощью программного обеспечения, но это занимает много времени. Мне нужно сделать над MySQL.

Моя таблица даты (дата>% d.% M.% Y% H:% i:% s);

ID  |   Date
----+-----------------------
246 |   11.08.2014 07:54:38
247 |   11.08.2014 07:55:11
248 |   11.08.2014 07:55:45
249 |   11.08.2014 07:56:20
250 |   11.08.2014 07:56:53
251 |   11.08.2014 07:57:26
252 |   11.08.2014 07:58:01
253 |   11.08.2014 07:58:35
254 |   11.08.2014 07:59:10
255 |   11.08.2014 07:59:49
256 |   11.08.2014 07:59:58
257 |   11.08.2014 08:00:15
258 |   11.08.2014 08:00:23
259 |   11.08.2014 08:00:58
260 |   11.08.2014 08:01:01
261 |   11.08.2014 08:01:08
262 |   11.08.2014 09:12:11

Ожидаемый результат:

mainID  |   startDate               |   finishDate              |   dateRangeIDs
--------+---------------------------+---------------------------+-----------------
246     |   11.08.2014 07:54:38     |   11.08.2014 07:59:10     |   247,248,249,250,251,252,253,254 
255     |   11.08.2014 07:59:49     |   11.08.2014 08:01:08     |   256,257,258,259,260,261
262     |   11.08.2014 09:12:11     |   NULL                    |   NULL
  • 0
    См. Meta.stackoverflow.com/questions/333952/…
  • 0
    Какую версию MySQL вы используете?
Показать ещё 2 комментария
Теги:
date
time
range
chain

1 ответ

0
Лучший ответ

Простейший метод использует lag() для получения предыдущего значения даты. Это не доступно в большинстве версий MySQL. Коррелятивный подзапрос действительно больно, чтобы сделать работу. Последним вариантом являются переменные:

select min(id) as mainid, min(date), max(date),
       group_concat(id order by id) as ids
from (select t.*,
             (@grp := if(@prev_date > date - interval 36 second,
                         if(@prev_date := date, @grp, @grp),  -- keep the group the same
                         if(@prev_date := date, @grp + 1, @grp + 1)
                        )
             ) as grp
      from (select t.*
            from t
            order by date
           ) t cross join
           (select @prev_date := '', @grp := 0) params
     ) t
group by grp;

РЕДАКТИРОВАТЬ:

Вы можете удалить основной идентификатор, выполнив:

select min(id) as mainid, min(date), max(date),
       substr(group_concat(id order by id), length(min(id)) + 1) as ids
  • 0
    Спасибо за ответ. Это был близкий результат. Идентификаторы группировки не являются последовательными, и каждая группа также получает свой собственный идентификатор. Как его разрешить? sqlfiddle.com/#!9/609e15/7
  • 0
    Первая проблема легко решается. Второе требует совсем немного работы. Это действительно того стоит?
Показать ещё 1 комментарий

Ещё вопросы

Сообщество Overcoder
Наверх
Меню