9.24. Сравнения строк и массивов#

9.24. Сравнения строк и массивов

9.24. Сравнения строк и массивов

Этот раздел описывает несколько специализированных конструкций для сравнения между группами значений. Эти формы синтаксически связаны с формами подзапросов предыдущего раздела, но не включают подзапросы. Формы, включающие массивные подвыражения, являются расширениями Tantor BE; остальные совместимы с SQL. Все формы выражений, документированные в этом разделе, возвращают логические (true/false) результаты.

9.24.1. IN

expression IN (value [, ...])

Правая сторона - это список выражений в скобках. Результат будет истинным, если результат выражения слева равен любому из выражений справа. Это сокращенная запись для

expression = value1
OR
expression = value2
OR
...

Обратите внимание, что если левое выражение возвращает null, или если нет равных значений справа и хотя бы одно правое выражение возвращает null, результат конструкции IN будет null, а не false. Это соответствует обычным правилам SQL для логических комбинаций null значений.

9.24.2. NOT IN

expression NOT IN (value [, ...])

Правая сторона - это список выражений в скобках. Результат будет истинным, если результат выражения слева не равен всем выражениям справа. Это сокращенная запись для

expression <> value1
AND
expression <> value2
AND
...

Обратите внимание, что если левое выражение возвращает null или если нет равных значений справа и хотя бы одно выражение справа возвращает null, результат конструкции NOT IN будет null, а не true, как можно было бы ожидать. Это соответствует обычным правилам SQL для логических комбинаций null значений.

Подсказка

x NOT IN y эквивалентно NOT (x IN y) во всех случаях. Однако, значения null гораздо чаще могут запутать новичка при работе с NOT IN, чем при работе с IN. Лучше выражать условие положительно, если это возможно.

9.24.3. ANY/SOME (array)

expression operator ANY (array expression)
expression operator SOME (array expression)

Правая сторона - это выражение в скобках, которое должно давать значение массива. Левое выражение вычисляется и сравнивается с каждым элементом массива с использованием заданного operator, который должен давать логический результат. Результат ANY равен true, если получен хотя бы один истинный результат. Результат равен false, если истинный результат не найден (включая случай, когда массив не содержит элементов).

Если выражение массива дает пустой массив, результатом оператора ANY будет null. Если левое выражение дает null, результатом оператора ANY обычно будет null (хотя нестрогий оператор сравнения может дать другой результат). Также, если правый массив содержит null элементы и не получается истинный результат сравнения, результатом оператора ANY будет null, а не false (снова, при условии строгого оператора сравнения). Это соответствует обычным правилам SQL для логических комбинаций null значений.

SOME является синонимом для ANY.

9.24.4. ALL (array)

expression operator ALL (array expression)

Правая сторона - это выражение в скобках, которое должно давать значение массива. Левое выражение вычисляется и сравнивается с каждым элементом массива с использованием заданного operator, который должен давать логический результат. Результат ALL будет true, если все сравнения дадут true (включая случай, когда массив не содержит элементов). Результат будет false, если найден хотя бы один false результат.

Если выражение массива дает пустой массив, результатом операции ALL будет null. Если левое выражение дает null, результат операции ALL обычно будет null (хотя нестрогий оператор сравнения может дать другой результат). Также, если правый массив содержит null элементы и не получается ложный результат сравнения, результатом операции ALL будет null, а не true (снова, при условии строгого оператора сравнения). Это соответствует обычным правилам SQL для логических комбинаций null значений.

9.24.5. Сравнение конструктора строк

row_constructor operator row_constructor

Каждая сторона является конструктором строки, как описано в Раздел 4.2.13. Оба конструктора строк должны иметь одинаковое количество полей. Указанный operator применяется к каждой паре соответствующих полей. (Поскольку поля могут быть разных типов, это означает, что для каждой пары может быть выбран разный конкретный оператор.) Все выбранные операторы должны быть членами какого-либо класса операторов B-дерева, или быть отрицанием члена = класса операторов B-дерева, что означает, что сравнение конструкторов строк возможно только когда operator является =, <>, <, <=, >, или >=, или имеет семантику, аналогичную одной из этих.

Случаи с использованием = и <> работают немного иначе, чем остальные. Две строки считаются равными, если все их соответствующие элементы не являются нулевыми и равны между собой; строки считаются неравными, если хотя бы один из соответствующих элементов не является нулевым и не равен другому; в противном случае результат сравнения строк неизвестен (null).

Для случаев <, <=, > и >= элементы строки сравниваются слева направо, останавливаясь, как только найдена неравная или нулевая пара элементов. Если хотя бы один из этой пары элементов является нулевым, результат сравнения строк неизвестен (null); в противном случае результат определяется сравнением этой пары элементов. Например, ROW(1,2,NULL) < ROW(1,3,0) дает значение true, а не null, потому что третья пара элементов не учитывается.

Примечание

До версии PostgreSQL 8.2, случаи <, <=, > и >= не обрабатывались в соответствии с SQL-спецификацией. Сравнение вида ROW(a,b) < ROW(c,d) реализовывалось как a < c AND b < d, в то время как правильное поведение эквивалентно a < c OR (a = c AND b < d).

row_constructor IS DISTINCT FROM row_constructor

Эта конструкция похожа на сравнение строк <>, но она не возвращает null для null-входных данных. Вместо этого любое null-значение считается неравным (отличным) от любого ненулевого значения, и любые два null-значения считаются равными (неотличимыми). Таким образом, результат будет либо true, либо false, но никогда null.

row_constructor IS NOT DISTINCT FROM row_constructor

Эта конструкция аналогична сравнению строк =, но она не возвращает значение null для пустых входных данных. Вместо этого любое пустое значение считается неравным (отличным) от любого значения not-null, и любые два пустых значения считаются равными (неотличимыми). Таким образом, результат всегда будет либо true, либо false, никогда null.

9.24.6. Сравнение составного типа

record operator record

Спецификация SQL требует, чтобы сравнение построчно возвращало NULL, если результат зависит от сравнения двух NULL значений или NULL и ненулевого значения. Tantor BE делает это только при сравнении результатов двух конструкторов строк (как в Раздел 9.24.5) или сравнении конструктора строки с результатом подзапроса (как в Раздел 9.23). В других контекстах, где сравниваются два значения составного типа, два NULL значения поля считаются равными, а NULL считается больше ненулевого значения. Это необходимо для обеспечения последовательного поведения сортировки и индексации для составных типов.

Каждая сторона вычисляется и они сравниваются построчно. Сравнения составных типов разрешены, когда operator равен =, <>, <, <=, > или >=, или имеет семантику, аналогичную одному из них. (А именно, оператор может быть оператором сравнения строк, если он является членом класса операторов B-дерева или является отрицанием члена = класса операторов B-дерева). Поведение по умолчанию для вышеуказанных операторов такое же, как для IS [ NOT ] DISTINCT FROM для конструкторов строк (см. Раздел 9.24.5).

Для поддержки сопоставления строк, которые включают элементы без операторного класса B-дерева по умолчанию, определены следующие операторы для сравнения составного типа: *=, *<>, *<, *<=, *> и *>=. Эти операторы сравнивают внутреннее двоичное представление двух строк. Две строки могут иметь разное двоичное представление, даже если сравнение двух строк с оператором равенства истинно. Порядок строк при использовании этих операторов сравнения является детерминированным, но в остальном не имеет смысла. Эти операторы используются внутренне для материализованных представлений и могут быть полезны для других специализированных целей, таких как репликация и дедупликация B-дерева (см. Раздел 64.4.3). Однако они не предназначены для общего использования при написании запросов.