Перейти к основному содержимому
Перейти к основному содержимому

Условные функции

if

Выполняет условную ветвление.

Если условие cond оценивается в ненулевое значение, функция возвращает результат выражения then. Если cond оценивается в ноль или NULL, то возвращается результат выражения else.

Настройка short_circuit_function_evaluation управляет тем, используется ли краткая оценка. Если включена, выражение then оценивалось только для строк, где cond равно true, а выражение else - для строк, где cond равно false. Например, при краткой оценке исключение деления на ноль не выбрасывается при выполнении запроса SELECT if(number = 0, 0, intDiv(42, number)) FROM numbers(10).

then и else должны быть похожими по типу.

Синтаксис

Псевдоним: cond ? then : else (тернарный оператор)

Аргументы

  • cond – Оцениваемое условие. UInt8, Nullable(UInt8) или NULL.
  • then – Выражение, возвращаемое, если condition истинно.
  • else – Выражение, возвращаемое, если condition ложно или NULL.

Возвращаемые значения

Результат любого из выражений then или else, в зависимости от условия cond.

Пример

Результат:

multiIf

Позволяет записывать оператор CASE компактнее в запросе.

Синтаксис

Настройка short_circuit_function_evaluation управляет тем, используется ли краткая оценка. Если включена, выражение then_i оценивается только для строк, где ((NOT cond_1) AND (NOT cond_2) AND ... AND (NOT cond_{i-1}) AND cond_i) равно true, cond_i будет оцениваться только для строк, где ((NOT cond_1) AND (NOT cond_2) AND ... AND (NOT cond_{i-1})) равно true. Например, при краткой оценке исключение деления на ноль не выбрасывается при выполнении запроса SELECT multiIf(number = 2, intDiv(1, number), number = 5) FROM numbers(10).

Аргументы

Функция принимает 2N+1 параметров:

  • cond_N — N-е оцениваемое условие, которое управляет тем, будет ли возвращено then_N.
  • then_N — Результат функции, когда cond_N истинно.
  • else — Результат функции, если ни одно из условий не истинно.

Возвращаемые значения

Результат любого из выражений then_N или else, в зависимости от условий cond_N.

Пример

Предположим, есть такая таблица:

Использование условных результатов напрямую

Условные функции всегда возвращают 0, 1 или NULL. Поэтому вы можете использовать условные результаты напрямую вот так:

NULL-значения в условных функциях

Когда в условных выражениях участвуют значения NULL, результат также будет NULL.

Поэтому вам следует осторожно составлять свои запросы, если типы являются Nullable.

Следующий пример демонстрирует это, не добавляя условие равенства в multiIf.

greatest

Возвращает наибольшее значение из списка значений. Все члены списка должны быть сопоставимыми по типу.

Примеры:

примечание

Возвращаемый тип - Float64, так как UInt8 должен быть повышен до 64 бит для сравнения.

примечание

Возвращаемый тип - DateTime64, так как DateTime32 должен быть повышен до 64 бит для сравнения.

least

Возвращает наименьшее значение из списка значений. Все члены списка должны быть сопоставимыми по типу.

Примеры:

примечание

Возвращаемый тип - Float64, так как UInt8 должен быть повышен до 64 бит для сравнения.

примечание

Возвращаемый тип - DateTime64, так как DateTime32 должен быть повышен до 64 бит для сравнения.

clamp

Ограничивает возвращаемое значение между A и B.

Синтаксис

Аргументы

  • value – Входное значение.
  • min – Ограничение нижней границы.
  • max – Ограничение верхней границы.

Возвращаемые значения

Если значение меньше минимального, возвращается минимальное значение; если больше максимального, возвращается максимальное значение; в противном случае возвращается текущее значение.

Примеры:

Оператор CASE

Выражение CASE в ClickHouse предоставляет условную логику, аналогичную оператору SQL CASE. Оно оценивает условия и возвращает значения на основе первого совпадающего условия.

ClickHouse поддерживает две формы CASE:

  1. CASE WHEN ... THEN ... ELSE ... END

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

  1. CASE <expr> WHEN <val1> THEN ... WHEN <val2> THEN ... ELSE ... END

Эта более компактная форма оптимизирована для сопоставления значений констант и использует caseWithExpression() внутри.

Например, следующее является допустимым:

Эта форма также не требует, чтобы возвращаемые выражения были константами.

Замечания

ClickHouse определяет тип результата выражения CASE (или его внутреннего эквивалента, например multiIf) до оценки любых условий. Это важно, когда возвращаемые выражения отличаются по типу, например, разные временные зоны или числовые типы.

  • Тип результата выбирается на основе наибольшего совместимого типа среди всех ветвей.
  • После выбора этого типа все другие ветви неявно приводятся к нему - даже если их логика никогда не будет выполнена во время выполнения.
  • Для типов, таких как DateTime64, где временная зона является частью сигнатуры типа, это может привести к неожиданному поведению: первая встреченная временная зона может быть использована для всех ветвей, даже если другие ветви указывают на разные временные зоны.

Например, ниже все строки возвращают временную метку в часовом поясе первой соответствующей ветви, т.е. Asia/Kolkata

Здесь ClickHouse видит несколько типов DateTime64(3, <timezone>). Он выводит общий тип как DateTime64(3, 'Asia/Kolkata', так как это первый, который он видит, неявно приводя другие ветви к этому типу.

Это можно решить, преобразовав в строку, чтобы сохранить предполагаемое форматирование временной зоны: