Skip to content

SQL JOIN 详解

对比 SQL JOIN 的各种类型:inner、outer、cross、self、lateral、natural——每种返回什么,并附一行示例。

JOIN 按共享键组合两个表中的行。当键匹配、不匹配或重复时,连接类型决定哪些行会保留。

参考表格 · 8 条目
8 of 8 rows
内连接与外连接
仅返回 ON 条件在两个表中都匹配的行。两侧未匹配的行都会被丢弃。SELECT u.name, o.total FROM users u INNER JOIN orders o ON u.id = o.user_id;
左表的全部行。没有匹配的地方右侧列为 NULL。SELECT u.name, o.total FROM users u LEFT OUTER JOIN orders o ON u.id = o.user_id;
右表的全部行。没有匹配的地方左侧列为 NULL。SELECT u.name, o.total FROM users u RIGHT OUTER JOIN orders o ON u.id = o.user_id;
两个表的全部行。未匹配的一侧用 NULL 填充。SELECT u.name, o.total FROM users u FULL OUTER JOIN orders o ON u.id = o.user_id;
交叉与自连接
笛卡尔积。每个左侧行与每个右侧行配对。没有 ON 子句。SELECT u.name, o.total FROM users u CROSS JOIN orders o;
通过别名将表与自身连接。比较单个表内部的行。SELECT a.id AS o1, b.id AS o2 FROM orders a JOIN orders b ON a.user_id = b.user_id WHERE a.id < b.id;
高级
FROM 中的子查询,针对每个外层行求值一次。子查询可以引用外层表的列。SELECT u.name, o.total FROM users u, LATERAL (SELECT total FROM orders WHERE user_id = u.id LIMIT 1) o;
按同名列连接。没有 ON 子句。当心意外的键冲突。SELECT u.name, o.total FROM users u NATURAL JOIN orders o;