WINDOW¶
Операция WINDOW
может использоваться для агрегирования по соседним документам, или предшествующим и/или последующим строкам, другими словами. Она также может агрегировать на основе значения или диапазона длительности относительно атрибута документа.
Операция выполняет COLLECT AGGREGATE
-подобную операцию над набором строк запроса. Однако если операция COLLECT
группирует несколько строк запроса в одну группу результатов, то операция WINDOW
выдает результат для каждой строки запроса:
- Строка, для которой происходит оценка функции, называется текущей строкой.
- Строки запроса, связанные с текущей строкой, над которой происходит оценка функции, составляют рамку окна для текущей строки.
Рамки окон определяются относительно текущего ряда:
- Определив рамку окна как все строки от начала запроса до текущей строки, можно вычислить текущие итоги для каждой строки.
- Определив рамку, простирающуюся на N строк по обе стороны от текущей строки, вы можете вычислить скользящие средние.
Синтаксис¶
Существует два варианта синтаксиса для операций WINDOW
.
На основе строк (смежные документы):
WINDOW { preceding: numPrecedingRows, following: numFollowingRows } AGGREGATE variableName = aggregateExpression
Range-based (диапазон значений или продолжительности):
WINDOW rangeValue WITH { preceding: offsetPreceding, following: offsetFollowing } AGGREGATE variableName = aggregateExpression
В агрегатных выражениях поддерживаются вызовы следующих функций:
LENGTH()
/COUNT()
MIN()
MAX()
SUM()
AVERAGE()
/AVG()
STDDEV_POPULATION()
/STDDEV()
STDDEV_SAMPLE()
VARIANCE_POPULATION()
/VARIANCE()
VARIANCE_SAMPLE()
UNIQUE()
SORTED_UNIQUE()
COUNT_DISTINCT()
/COUNT_UNIQUE()
BIT_AND()
BIT_OR()
BIT_XOR()
Агрегирование по строкам¶
Первая синтаксическая форма WINDOW
позволяет агрегировать по фиксированному количеству строк, следующих или предшествующих текущей строке. Также можно определить, что все предшествующие или последующие строки должны быть агрегированы (неограниченно
). Количество строк должно быть определено во время компиляции запроса.
Приведенный ниже запрос демонстрирует использование оконных фреймов для вычисления пробегающих итогов, а также пробегающих средних, вычисляемых по текущей строке и строкам, непосредственно предшествующим и следующим за ней:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 |
|
Порядок строк контролируется операцией SORT
над атрибутом time
.
Первая операция WINDOW
объединяет предыдущий, текущий и следующий ряд (предшествующий и последующий имеют значение 1) и вычисляет среднее и сумму этих трех значений. В случае первого ряда нет предыдущего ряда, но есть следующий ряд, поэтому значения 10
и 0
складываются для вычисления суммы, которая делится на 2 для вычисления среднего значения. Для второго ряда значения 10
, 0
и 9
суммируются и делятся на 3, и так далее.
Вторая операция WINDOW
объединяет все предыдущие значения (не ограниченные) для вычисления текущей суммы. Для первого ряда это просто 10
, для второго - 10
+ 0
, для третьего 10
+ 0
+ 9
, и так далее.
time | subject | val | rollingAverage | rollingSum | cumulativeSum | cumulativeSum |
---|---|---|---|---|---|---|
2021-05-25 07:00:00 | st113 | 10 | 5 | 10 | 10 | 10 |
2021-05-25 07:00:00 | xh458 | 0 | 6.333... | 19 | 10 | |
2021-05-25 07:15:00 | st113 | 9 | 6.333... | 19 | 19 | 19 |
2021-05-25 07:15:00 | xh458 | 10 | 14.666... | 44 | 29 | |
2021-05-25 07:30:00 | st113 | 25 | 13.333... | 40 | 54 | |
2021-05-25 07:30:00 | xh458 | 5 | 16.666... | 50 | 59 | |
2021-05-25 07:45:00 | st113 | 20 | 18.333... | 55 | 79 | |
2021-05-25 07:45:00 | xh458 | 30 | 25 | 75 | 109 | |
2021-05-25 08:00:00 | xh458 | 25 | 27.5 | 55 | 134 |
Приведенный ниже запрос демонстрирует использование оконных рамок для вычисления текущих итогов в каждой subject
группе упорядоченных по времени
строк запроса, а также скользящих сумм и средних, вычисленных по текущей строке и строкам, непосредственно предшествующим и следующим за ней, также по subject
группе и отсортированных по времени
:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 |
|
Если посмотреть на первый ряд с темой xh458
, то можно увидеть, что кумулятивная сумма обнулилась и что скользящее среднее и сумма не учитывают предыдущий ряд, принадлежащий теме st113
.
time | subject | val | rollingAverage | rollingSum | cumulativeSum | cumulativeSum |
---|---|---|---|---|---|---|
2021-05-25 07:00:00 | st113 | 10 | 9.5 | 19 | 10 | 10 |
2021-05-25 07:15:00 | st113 | 9 | 14.666... | 44 | 19 | |
2021-05-25 07:30:00 | st113 | 25 | 18 | 54 | 44 | 2021-05-25 07:30:00 |
2021-05-25 07:45:00 | st113 | 20 | 22.5 | 45 | 64 | |
2021-05-25 07:00:00 | xh458 | 0 | 5 | 10 | 0 | 0 |
2021-05-25 07:15:00 | xh458 | 10 | 5 | 15 | 10 | 10 |
2021-05-25 07:30:00 | xh458 | 5 | 15 | 45 | 15 | |
2021-05-25 07:45:00 | xh458 | 30 | 20 | 60 | 45 | |
2021-05-25 08:00:00 | xh458 | 25 | 27.5 | 55 | 70 |
Агрегация на основе диапазона¶
Вторая синтаксическая форма WINDOW
позволяет агрегировать по всем документам в пределах диапазона значений. Смещение - это разница в значениях атрибутов по сравнению с текущим документом.
Значения атрибутов должны быть числовыми. Вычисления смещения выполняются путем сложения или вычитания числовых смещений, указанных в атрибутах following
и preceding
. Числа смещения должны быть положительными и должны быть определены во время компиляции запроса. По умолчанию смещение равно 0
.
Синтаксис окна на основе диапазона требует, чтобы входные строки были отсортированы по значению строки. Для обеспечения корректности результата оптимизатор AQL автоматически вставит в запрос оператор SORT
перед оператором WINDOW
. В дальнейшем оптимизатор может отказаться от этого оператора SORT
, если для групповых критериев имеется индекс сортировки.
Следующий запрос демонстрирует использование оконных фреймов для вычисления итогов, а также средних значений, вычисленных на основе текущего документа и документов, имеющих значения атрибутов в t.val
в диапазоне [-10, +5]
(включительно), предшествующих и последующих:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
|
Диапазон значений первой строки - [-10, 5]
, так как val
- 0
, поэтому значения из первой и второй строки складываются до 5
, а среднее значение равно 2.5
. Диапазон значений последней строки - [20, 35]
, так как val
- 30
, что означает, что последние четыре строки суммируются до суммы 100
и среднего значения 25
(диапазон включительно, т.е. val
попадает в диапазон со значением 20
).
time | subject | val | rollingAverage | rollingSum |
---|---|---|---|---|
2021-05-25 07:00:00 | xh458 | 0 | 2.5 | 5 |
2021-05-25 07:30:00 | xh458 | 5 | 6.8 | 34 |
2021-05-25 07:15:00 | st113 | 9 | 6.8 | 34 |
2021-05-25 07:00:00 | st113 | 10 | 6.8 | 34 |
2021-05-25 07:15:00 | xh458 | 10 | 6.8 | 34 |
2021-05-25 07:45:00 | st113 | 20 | 18 | 90 |
2021-05-25 07:30:00 | st113 | 25 | 25 | 100 |
2021-05-25 08:00:00 | xh458 | 25 | 25 | 25 |
2021-05-25 07:45:00 | xh458 | 30 | 25 | 100 |
Агрегирование по временным интервалам¶
Агрегирование по временным интервалам - это подтип агрегирования на основе диапазона, который использует вторую синтаксическую форму WINDOW
, но с длительностями ISO.
Для поддержки фреймов WINDOW
над данными временных рядов операция WINDOW
может вычислять смещения временных меток, используя положительные строки длительности ISO 8601, например P1Y6M
(1 год и 6 месяцев) или PT12H30M
(12 часов и 30 минут). Также смотрите Функции даты. В отличие от стандарта ISO 8601, компоненты недели могут свободно комбинироваться с другими компонентами. Например, P1WT1H
и P1M1W
являются допустимыми. Дробные значения поддерживаются только для секунд, и только с точностью до трех десятичных знаков после разделителя, т.е. с точностью до миллисекунды. Например, PT0.123S
является допустимой продолжительностью, а PT0.5H
и PT0.1234S
- нет.
Длительности могут быть указаны отдельно в following
и preceding
. Если используется такая длительность, то значение атрибута текущего документа должно быть числом и рассматривается как числовой timestamp в миллисекундах. Диапазон включительно. Если ни одна из границ не указана, она рассматривается как пустая длительность (т.е. P0D
).
Следующий запрос демонстрирует использование оконных фреймов для вычисления скользящих сумм и средних по наблюдениям за последние 30 минут (включительно) на основе атрибута документа time
, который преобразуется из строки времени даты в числовую метку времени:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
|
При времени 07:30:00
все, что происходит с 07:00:00
до 07:30:00
в тот же день, попадает в диапазон продолжительности с предшествующим: "PT30M"
, таким образом, агрегируя шесть верхних строк с суммой 59
и средним значением 9.8333...
.
time | subject | val | rollingAverage | rollingSum |
---|---|---|---|---|
2021-05-25 07:00:00 | st113 | 10 | 5 | 10 |
2021-05-25 07:00:00 | xh458 | 0 | 5 | 10 |
2021-05-25 07:15:00 | st113 | 9 | 7.25 | 29 |
2021-05-25 07:15:00 | xh458 | 10 | 7.25 | 29 |
2021-05-25 07:30:00 | st113 | 25 | 9.8333... | 59 |
2021-05-25 07:30:00 | xh458 | 5 | 9.8333... | 59 |
2021-05-25 07:45:00 | st113 | 20 | 16.5 | 99 |
2021-05-25 07:45:00 | xh458 | 30 | 16.5 | 99 |
2021-05-25 08:00:00 | xh458 | 25 | 21 | 105 |