2015-05-31 4 views
2

У меня есть большой набор измерений, сделанных каждые 1 миллисекунда, хранящихся в таблице SQL Server 2012. Всякий раз, когда в некоторых строках есть 3 или более повторяющихся значения, я хотел бы удалить средние дубликаты. Выделенные значения в этом образце данных образца - это те, которые я хочу удалить. Есть ли способ сделать это с помощью SQL-запроса?Удаление дубликатов во временных рядах

SampleData

+0

Вы можете сказать нам версию SQL Server? Это говорит нам о том, являются ли функции оконной обработки опцией –

+0

В этом вопросе говорится о SQL 2012. Мне очень интересно посмотреть, как они будут работать (я их никогда не использовал). – Alan

+0

Версия сервера - 2012 Express. – JPoole

ответ

3

Вы можете сделать это с помощью CTE и ROW_NUMBER:

SQL Fiddle

WITH CteGroup AS(
    SELECT *, 
     grp = ROW_NUMBER() OVER(ORDER BY MS) - ROW_NUMBER() OVER(PARTITION BY Value ORDER BY MS) 
    FROM YourTable 
), 
CteFinal AS(
    SELECT *, 
     RN_FIRST = ROW_NUMBER() OVER(PARTITION BY grp, Value ORDER BY MS), 
     RN_LAST = ROW_NUMBER() OVER(PARTITION BY grp, Value ORDER BY MS DESC) 
    FROM CteGroup 
) 
DELETE 
FROM CteFinal 
WHERE 
    RN_FIRST > 1 
    AND RN_LAST > 1 
+1

Это почти работает. Но, если предшествовать точке данных и следовать равным значениям, она удаляется. Пример: 20,20,40,20,20 - 40 удаляется, когда этого не должно быть. Я попытался изменить предложение where на «LG = LD и LG = Value», но это выглядело некорректно. – JPoole

+0

Я подозреваю, что здесь должно быть 'WHERE RN_FIRST <> 1 И RN_LAST <> 1' –

+0

@GiorgiNakeuri, я считаю '' 'будет достаточно, поскольку' ROW_NUMBER' начинается с '1', или я что-то упускаю? –

0

Да есть

select * from table group by table.field ->value 
+0

это не учитывает порядок значений. – Jerome

1

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

DELETE FROM tbl 
WHERE ms IN 
(
    SELECT T.ms 
    FROM tbl T 
    INNER JOIN tbl T1 ON T.ms = T1.ms + 1 
    INNER JOIN tbl T2 ON T.ms = T2.ms - 1 
    WHERE T.value = T1.value AND T.value = T2.value 
) 

Если стол действительно большой, я могу видеть этот дующий темпдб.

Смежные вопросы