2025年9月25日: PostgreSQL 18 发布!
支持的版本: 当前 (18) / 17 / 16 / 15 / 14 / 13
开发版本: devel
不支持的版本: 12 / 11 / 10 / 9.6 / 9.5 / 9.4 / 9.3 / 9.2 / 9.1 / 9.0 / 8.4 / 8.3 / 8.2 / 8.1 / 8.0 / 7.4 / 7.3 / 7.2 / 7.1

7.4. 合并查询 (UNION, INTERSECT, EXCEPT) #

可以使用集合操作 union、intersection 和 difference 来合并两个查询的结果。语法如下:

query1 UNION [ALL] query2
query1 INTERSECT [ALL] query2
query1 EXCEPT [ALL] query2

其中 query1query2 是可以利用到目前为止讨论过的任何特性的查询。

UNION 会将 query2 的结果附加到 query1 的结果之后(尽管不保证行实际返回的顺序)。此外,它会从结果中删除重复行,方式与 DISTINCT 相同,除非使用了 UNION ALL

INTERSECT 返回 query1 的结果集和 query2 的结果集中都存在的行。除非使用了 INTERSECT ALL,否则会删除重复行。

EXCEPT 返回 query1 的结果集中存在但 query2 的结果集中不存在的行。(有时也称为两个查询的差集。)同样,除非使用了 EXCEPT ALL,否则会删除重复行。

为了计算两个查询的 union、intersection 或 difference,这两个查询必须是union 兼容,这意味着它们返回的列数相同,并且对应列的数据类型兼容,具体描述参见10.5 节

集合操作可以合并,例如:

query1 UNION query2 EXCEPT query3

这等同于:

(query1 UNION query2) EXCEPT query3

如这里所示,您可以使用括号来控制求值顺序。没有括号时,UNIONEXCEPT 是从左到右结合的,但 INTERSECT 的优先级高于这两个操作符。因此:

query1 UNION query2 INTERSECT query3

意味着:

query1 UNION (query2 INTERSECT query3)

您也可以用括号将单个 query 括起来。如果 query 需要使用后面章节讨论的任何子句,例如 LIMIT,这一点就很重要。没有括号,您会遇到语法错误,或者该子句将被理解为应用于集合操作的输出而不是其输入之一。例如:

SELECT a FROM b UNION SELECT x FROM y LIMIT 10

是可以接受的,但它的意思是:

(SELECT a FROM b UNION SELECT x FROM y) LIMIT 10

而不是:

SELECT a FROM b UNION (SELECT x FROM y LIMIT 10)

提交更正

如果您在文档中发现任何不正确、不符合您对特定功能的体验或需要进一步阐明的内容,请使用此表格报告文档问题。