Самостоятельное объединение данных временных рядов - PullRequest
3 голосов
/ 02 февраля 2010

Мне нужна помощь с тем, что, на мой взгляд, должно быть довольно простым запросом самостоятельного объединения. Просто нужно объединить совпадающее время начала и окончания двух записей в одну запись

Скажи, что у меня в таблице есть следующее

Time  Event
08:00 Start
09:00 Stop
10:30 Start
10:45 Stop
11:00 Start
11:15 Start
12:00 Stop
12:30 Stop

Я хочу такой вид

StartTime Stoptime
08:00  09:00 
10:30  10:45 
11:00 
11:15  12:00 
       12:30 

Обратите внимание, что он должен найти ближайшее время начала или окончания сопоставления. Если по какой-либо причине нет подходящего события, его следует оставить пустым.

Спасибо

Ответы [ 2 ]

4 голосов
/ 02 февраля 2010

отказ от ответственности: Я бы серьезно подумал о другой конструкции стола.Присоединение к датам или временам никогда не является хорошей идеей.Если у вас был идентификатор запускаемого события, вы можете легко ВЕРНУТЬСЯ, ЧТОБЫ попытаться найти соответствующий конец этого события.

Для SQL Server попробуйте:

DECLARE @Events  table (EventTime char(5), EventType varchar(5))

INSERT INTO @Events VALUES ('08:00','Start')
INSERT INTO @Events VALUES ('09:00','Stop')
INSERT INTO @Events VALUES ('10:30','Start')
INSERT INTO @Events VALUES ('10:45','Stop')
INSERT INTO @Events VALUES ('11:00','Start')
INSERT INTO @Events VALUES ('11:15','Start')
INSERT INTO @Events VALUES ('12:00','Stop')
INSERT INTO @Events VALUES ('12:30','Stop')

SELECT
    dt.StartTime, dt.StopTime
    FROM (SELECT
              p.EventTime AS StartTime,CASE WHEN c.EventType!='Stop' THEN NULL ELSE c.EventTime END AS StopTime
                  ,p.EventTime AS SortBy
              FROM @Events          p
                INNER JOIN @Events  c ON p.EventTime<c.EventTime
              WHERE p.EventType='Start'
                  AND c.EventTime=(SELECT MIN(EventTime) FROM @Events WHERE  EventTime>p.EventTime)
          UNION
          SELECT
              NULL AS StartTime,p.EventTime
                  ,p.EventTime AS SortBy
              FROM @Events          p
                INNER JOIN @Events  c ON p.EventTime>c.EventTime
              WHERE p.EventType='STOP'
                  AND c.EventTime=(SELECT MAX(EventTime) FROM @Events WHERE  EventTime<p.EventTime)
                  AND c.EventType='Stop'
         ) dt
    ORDER BY dt.SortBy

ВЫХОД:

StartTime StopTime
--------- --------
08:00     09:00
10:30     10:45
11:00     NULL
11:15     12:00
NULL      12:30

(5 row(s) affected)
0 голосов
/ 03 февраля 2010

Я предполагаю, что вы используете тег SQL для обозначения sql-server .Но в случае, если будущие искатели будут заинтересованы в решении Oracle, эту проблему можно решить с помощью аналитических функций LEAD() и LAG() ...

SQL> select * from (
  2      select case when event = 'Start' then t else null end as start_t
  3             , case when next_event = 'Stop' then next_t
  4                    when event = 'Stop' and prev_event = 'Stop' then next_t
  5                    else null end as stop_t
  6      from (
  7          select event
  8                  , t
  9                  , lead (t) over (order by t) as next_t
 10                  , lead (event) over (order by t) as next_event
 11                  , lag (event) over (order by t) as prev_event
 12          from t23
 13          order by t )
 14      )
 15  where start_t is not null
 16  or    stop_t is not null
 17  /

START STOP_
----- -----
08:00 09:00
10:30 10:45
11:00
11:15 12:00
      12:30

SQL>
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...