# 9.24.行和数组比较
本节描述了用于在值组之间进行多次比较的几种特殊结构。这些表单在语法上与上一节的子查询表单相关,但不涉及子查询。涉及数组子表达式的形式是PostgreSQL扩展;其余的都是SQL兼容的。本节中记录的所有表达式形式都返回布尔(真/假)结果。
# 9.24.1.在里面
expression IN (value [, ...])
右边是带括号的标量表达式列表。如果左侧表达式的结果等于任何右侧表达式,则结果为“true”。这是一个简写符号
expression = value1
OR
expression = value2
OR
...
请注意,如果左侧表达式生成null,或者如果没有相等的右侧值,并且至少有一个右侧表达式生成null,则在里面
构造将为null,而不是false。这符合SQL关于空值布尔组合的常规规则。
# 9.24.2.不在
expression NOT IN (value [, ...])
右边是带括号的标量表达式列表。如果左侧表达式的结果不等于所有右侧表达式,则结果为“true”。这是一个简写符号
expression <> value1
AND
expression <> value2
AND
...
请注意,如果左侧表达式生成null,或者如果没有相等的右侧值,并且至少有一个右侧表达式生成null,则不在
构造将为null,而不是人们天真地期望的那样为真。这符合SQL关于空值布尔组合的常规规则。
# 提示
x不在y中
相当于不是(x/y)
在所有情况下。然而,在使用空值时,新手更容易绊倒不在
而不是和你一起工作在里面
.如果可能的话,最好积极地表达你的病情。
# 9.24.3. 任何
/一些
(阵列)
expression operator ANY (array expression)
expression operator SOME (array expression)
右边是一个带括号的表达式,它必须产生一个数组值。使用给定的表达式计算左侧表达式,并与数组中的每个元素进行比较*操作人员
*,它必须产生一个布尔结果。结果任何
如果得到任何真实结果,则为“真”。如果没有找到真正的结果(包括数组有零个元素的情况),则结果为“false”。
如果数组表达式生成空数组,则任何
将为空。如果左侧表达式产生null,则任何
通常为null(尽管非严格比较运算符可能会产生不同的结果)。此外,如果右侧数组包含任何空元素,并且没有得到真正的比较结果,则任何
将为null,而不是false(同样,假设使用严格的比较运算符)。这符合SQL关于空值布尔组合的常规规则。
一些
是的同义词任何
.
# 9.24.4. 全部的
(阵列)
expression operator ALL (array expression)
右边是一个带括号的表达式,它必须产生一个数组值。使用给定的表达式计算左侧表达式,并与数组中的每个元素进行比较*操作人员
*,它必须产生一个布尔结果。结果全部的
如果所有比较结果都为真(包括数组有零个元素的情况),则为“真”。如果发现任何错误结果,则结果为“错误”。
如果数组表达式生成空数组,则全部的
将为空。如果左侧表达式产生null,则全部的
通常为null(尽管非严格比较运算符可能会产生不同的结果)。此外,如果右侧数组包含任何空元素,并且没有获得错误的比较结果,则全部的
将为null,而不是true(同样,假设使用严格的比较运算符)。这符合SQL关于空值布尔组合的常规规则。
# 9.24.5.行构造函数比较
row_constructor operator row_constructor
每一侧都是一个行构造函数,如中所述第4.2.13节.两行值的字段数必须相同。对每一侧进行评估,并按行进行比较。当*操作人员
*是=
, <>
, <
, <=
, >
或>=
。每个行元素的类型必须具有默认的B-树运算符类,否则尝试的比较可能会生成错误。
# 笔记
如果使用前面的列解决比较问题,则可能不会出现与元素数量或类型相关的错误。
这个=
和<>
案例的工作原理与其他案例略有不同。如果两行的所有对应成员都非空且相等,则认为这两行相等;如果任何对应的成员非空且不相等,则行不相等;否则,行比较的结果未知(null)。
对于<
, <=
, >
和>=
在某些情况下,行元素会从左到右进行比较,一旦发现元素对不相等或为空,就会立即停止。如果这对元素中的任何一个为null,则行比较的结果未知(null);否则,这对元素的比较将决定结果。例如行(1,2,空)<行(1,3,0)
因为不考虑第三对元素,所以产生true而不是null。
# 笔记
在PostgreSQL 8.2之前<
, <=
, >
和>=
没有按照SQL规范处理案例。像这样的比较第(a,b)行<第(c,d)行
作为a<c和b<d
而正确的行为相当于a<c或(a=c,b<d)
.
row_constructor IS DISTINCT FROM row_constructor
这个构造类似于<>
行比较,但它不会为空输入生成空值。相反,任何空值都被视为不等于(不同于)任何非空值,任何两个空值都被视为相等(不不同)。因此,结果要么为真,要么为假,永远不会为空。
row_constructor IS NOT DISTINCT FROM row_constructor
这个构造类似于=
行比较,但它不会为空输入生成空值。相反,任何空值都被视为不等于(不同于)任何非空值,任何两个空值都被视为相等(不不同)。因此,结果将始终为真或假,永远不会为空。
# 9.24.6.复合类型比较
record operator record
如果结果取决于比较两个空值或一个空值和一个非空值,SQL规范要求行比较返回NULL。PostgreSQL只有在比较两个行构造函数的结果时才会这样做(如第9.24.5节)或者将行构造函数与子查询的输出进行比较(如第9.23节)。在比较两个复合类型值的其他上下文中,两个空字段值被视为相等,空字段值被视为大于非空字段值。为了使复合类型具有一致的排序和索引行为,这是必要的。
对每一侧进行评估,并按行进行比较。当*操作人员
*是=
, <>
, <
, <=
, >
或>=
,或具有与其中一个类似的语义。(具体来说,如果运算符是B-树运算符类的成员,或者是=
B-树运算符类的成员。)上述运算符的默认行为与的相同与…不同
对于行构造函数(请参见第9.24.5节).
为了支持包含没有默认B树运算符类的元素的行的匹配,定义了以下用于复合类型比较的运算符:*=
, *<>
, *<
, *<=
, *>
和*>=
.这些运算符比较两行的内部二进制表示形式。两行可能具有不同的二进制表示形式,即使使用相等运算符对两行进行比较是正确的。这些比较运算符下的行顺序是确定的,但在其他方面没有意义。这些操作符在内部用于物化视图,对于复制和B-Tree重复数据消除等其他专门用途可能很有用(请参阅第64.4.3节)。不过,它们在编写查询时通常并不有用。