也许最强大的SQL功能是JOIN操作。这让所有非关系数据库羡慕不已,因为当你想“合并”两个数据集时,这个概念是如此简单,并且又普遍适用。 简单地说,连接两个表,就是将一个表中的每一行与另一个表中的每一行结合起来。来自SQL Masterclass的插图展示了这个原理。 参见我们最近关于使用Venn图来说明JOIN的文章。上面的插图比较了INNER JOIN和不同的OUTER JOIN操作,但是这些并不是所有的可能性。让我们从更系统的角度来看问题。 请注意,每当本文中我说“X发生在Y之前”时,我的意思是“逻辑上,X发生在Y之前”。数据库优化器仍然可以选择在X之前执行Y,因为这更快,而不改变结果。有关操作的语法/逻辑顺序的更多信息点击这里查看。 好的,让我们一个个查看所有的join类型吧! CROSS JOIN(交叉连接)最基本的JOIN操作是真正的笛卡尔乘积。它只是组合一个表中的每一行和另一个表中的每一行。维基百科通过一副卡片给出了笛卡尔乘积的最佳例子,交叉连接ranks表和suits表: 在现实世界的场景中,CROSS JOIN在执行报告时非常有用,例如,你可以生成一组日期(例如一个月的天数)并与数据库中的所有部门交叉连接,以创建完整的天/部门表。使用PostgreSQL语法: 想象一下,我们有以下数据: 现在结果将如下所示: -------- ------------ 现在,在每个天/部门组合中,你可以计算该部门的每日收入,或其他。 特点CROSS JOIN是笛卡尔乘积,即“乘法”中的乘积。数学符号使用乘号表示此操作:A×B,或在本文例子中:days×departments。 与“普通”算术乘法一样,如果两个表中有一个为空(大小为零),则结果也将为空(大小为零)。这是完全有道理的。如果我们将前面的31天与0个部门组合,我们将获得0天/部门组合。同样的,如果我们将空日期范围与任何数量的部门组合,我们也会获得0天/部门组合。 换一种说法: size(result) = size(days) * size(departments) 替代语法以前,在ANSI JOIN语法被引入到SQL之前,大家就会在FROM子句中写以逗号分隔的表格列表来编写CROSS JOIN。上面的查询等价于: SELECT *FROM generate_series( 一般来说,我强烈建议使用CROSS JOIN关键字,而不是以逗号分隔的表格列表,因为如果你有意地想要执行CROSS JOIN,那么没有什么可以比使用实际的关键字能更好地传达这个意图(对下一个开发人员而言)。何况用逗号分隔的表格列表中有这么多地方都有可能会出错。你肯定不希望看到这样的事情! INNER JOIN(Theta-JOIN)构建在先前的CROSS JOIN操作之上,INNER JOIN(或者只是简单的JOIN,有时也称为“THETA”JOIN)允许通过某些谓词过滤笛卡尔乘积的结果。大多数时候,我们把这个谓词放在ON子句中,它可能是这样的: SELECT * |
|
声明:文章版权归原作者所有 部分文章转自互联网 如有侵权请联系
[邮箱地址] 删除
|