#sql
#sql
Вопрос:
Моя цель — отфильтровать выбранные данные из огромной таблицы. Я работаю с огромной таблицей, содержащей миллионы строк данных, и мне нужно найти эффективный способ выбора нужных мне данных. Таблица содержит значения различных измерений, включая временную метку и имя:
Имя | временная метка | Значение |
---|---|---|
температура | 15:35 | 22 |
Скорость | 15:35 | 50 |
температура | 15:36 | 22 |
Скорость | 15:36 | 50 |
температура | 15:37 | 22 |
Скорость | 15:37 | 50 |
Скорость | 15:38 | 50 |
температура | 15:38 | 25 |
Я работаю с такими инструкциями
Select * from MeasurementValues where Name like 'speed'
Это возвращает мне значения, которые я затем помещаю в диаграмму. Проблема в том, что для размещения всех точек на этой диаграмме требуется слишком много времени. Поскольку точки в основном остаются с одним и тем же значением, я хочу добавить фильтрацию в свой оператор. я хочу группировать последовательные записи с одинаковыми значениями и возвращать только первую и последнюю запись.
Например, если я хочу иметь значения для скорости, мне нужны только результаты:
Имя | временная метка | Значение |
---|---|---|
Скорость | 15:35 | 50 |
Скорость | 15:38 | 50 |
Для значений температуры я хочу получить следующие результаты:
Имя | временная метка | Значение |
---|---|---|
температура | 15:35 | 22 |
температура | 15:37 | 22 |
температура | 15:38 | 25 |
Я надеюсь, что вы понимаете мою проблему и можете мне в этом помочь. Мои знания SQL довольно просты.
С уважением
Комментарии:
1. почему для ‘temperatire’ у вас есть 3 записи?
2. Первый — это Первый ряд с температурой 22, Второй — последний ряд со значением 22. После этого у меня есть значение 25, поэтому его тоже нужно получить
3. тогда как насчет третьей строки?
4. Извините, я отредактировал это. Значение изменяется на 25. Вот почему я тоже вставил эту строку туда.
Ответ №1:
Вы можете использовать lead()
и lag()
:
select mv.*
from (select mv.*,
lag(value) over (partition by name order by timestamp) as prev_value,
lead(value) over (partition by name order by timestamp) as next_value
from MeasurementValues mv
where name = 'speed'
) mv
where (prev_value is null or prev_value <> value) or
(next_value is null or next_value <> value);
Комментарии:
1. Я должен проверить это завтра. Опережение и отставание для меня в новинку, но, похоже, это делает именно то, что я хочу
2. Спасибо, это сработало отлично и было намного эффективнее, чем мой предыдущий код.