#sql #vertica
Вопрос:
Мой столик находится
ts | symbol | bid --------------------- -------- ------ 2009-01-01 03:00:00 | XYZ | 10 2009-01-01 03:00:03 | XYZ | 11 2009-01-01 03:00:06 | XYZ | 10.5 2009-01-01 03:00:09 | XYZ | 11 2009-01-01 03:00:00 | ABC | 10 2009-01-01 03:00:03 | ABC | 11 2009-01-01 03:00:06 | ABC | 11 2009-01-01 03:00:09 | ABC | 11
Я хочу запустить запрос , в котором я сначала получу все строки с символом ABC
, затем я хочу поместить их в окна на основе условия, а затем выбрать 2-е окно.
Подзапрос работает (если не используется подзапрос)
select * from (select ts, symbol, bid, conditional_true_event(bid gt; 10.6) over(order by ts) as window from Tickstore3 where symbol = 'ABC') as t3;
Выход:
ts | symbol | bid | window --------------------- -------- ----- -------- 2009-01-01 03:00:00 | ABC | 10 | 0 2009-01-01 03:00:03 | ABC | 11 | 1 lt;-- I want to get only this row 2009-01-01 03:00:06 | ABC | 11 | 2 2009-01-01 03:00:09 | ABC | 11 | 3
Но я не могу получить только 2-й ряд
select * from (select ts, symbol, bid, conditional_true_event(bid gt; 10.6) over(order by ts) as window from Tickstore3 where symbol = 'ABC') as t3 where window = 1;
Я получаю сообщение об ошибке:
ОШИБКА 4856: Синтаксическая ошибка в или рядом с «окном» в
строке 1 символа 151: …w из Tickstore3, где символ=’ABC’) как t3, где окно=1;
Комментарии:
1. Не уверен насчет vertica, но
window
может быть проблематичным идентификатором. Я бы поменял его на другой.2. @TheImpaler прав.
WINDOW
является ключевым словом, которое инициирует предложение именованного окна — зарезервированное слово. Никогда не используйте зарезервированные слова для имен объектов.
Ответ №1:
нашел ошибку. Я не могу ссылаться window
. Я должен использовать его с именем временного результата
select * from (select ts, symbol, bid, conditional_true_event(bid gt; 10.6) over(order by ts) as window from Tickstore3 where symbol='ABC') as t3 where t3.window=1 ; lt;-- note t3.window ts | symbol | bid | window --------------------- -------- ----- -------- 2009-01-01 03:00:03 | ABC | 11 | 1 (1 row)
Ответ №2:
Я думаю, что CONDITIONAL_TRUE_EVENT()
здесь это полный перебор.
Условная текущая сумма (с использованием CASE WHEN ...
выражения) подойдет очень хорошо.
И просто для удовольствия я добавляю предложение «именованное окно«, чтобы продемонстрировать, почему это зарезервированное слово — и я думаю counter
, что это более подходящее название для того, по чему вы хотите отфильтровать …
Правильные слова программиста могут сделать любую документацию или комментарий излишними, если вы сделаете мудрый выбор …
WITH -- your input ... tickstore(ts,symbol,bid) AS ( SELECT TIMESTAMP '2009-01-01 03:00:00','XYZ',10 UNION ALL SELECT TIMESTAMP '2009-01-01 03:00:03','XYZ',11 UNION ALL SELECT TIMESTAMP '2009-01-01 03:00:06','XYZ',10.5 UNION ALL SELECT TIMESTAMP '2009-01-01 03:00:09','XYZ',11 UNION ALL SELECT TIMESTAMP '2009-01-01 03:00:00','ABC',10 UNION ALL SELECT TIMESTAMP '2009-01-01 03:00:03','ABC',11 UNION ALL SELECT TIMESTAMP '2009-01-01 03:00:06','ABC',11 UNION ALL SELECT TIMESTAMP '2009-01-01 03:00:09','ABC',11 ) -- real query starts here, replace following comma with "WITH" ... , w_counter AS ( SELECT * , SUM(CASE WHEN bid gt; 10.6 THEN 1 END) OVER w AS counter FROM tickstore WHERE symbol='ABC' WINDOW w AS (ORDER BY ts) ) SELECT ts , symbol , bid , counter FROM w_counter WHERE counter=1 ; -- out ts | symbol | bid | counter -- out --------------------- -------- ------ --------- -- out 2009-01-01 03:00:03 | ABC | 11.0 | 1
Комментарии:
1. технически я не могу принять ваш ответ, поскольку он не решает конкретную проблему, с которой я сталкиваюсь. Тем не менее, он показывает правильный способ написания запроса. Спасибо