摘要:在本教程中,您将了解 MySQL LEFT JOIN
子句以及如何应用它来查询两个或多个表中的数据。
MySQL LEFT JOIN 子句简介
LEFT JOIN
允许您从两个或多个表查询数据。与INNER JOIN
子句类似, LEFT JOIN
是SELECT
语句的可选子句,它紧跟在FROM
子句之后。
假设您要连接两个表t1
和t2
。
以下语句显示如何使用LEFT JOIN
子句连接两个表:
SELECT
select_list
FROM
t1
LEFT JOIN t2 ON
join_condition;
Code language: SQL (Structured Query Language) (sql)
当使用LEFT JOIN
子句时,引入了左表和右表的概念。
在上面的语法中, t1
是左表, t2
是右表。
LEFT JOIN
子句从左表 ( t1
) 开始选择数据。它根据join_condition
将左表 ( t1
) 中的每一行与右表 ( t2
) 中的每一行进行匹配。
如果两个表中的行导致联接条件计算为true
,则LEFT JOIN
会将两个表中的行列合并为一个新行,并将该新行包含在结果行中。
如果左表 ( t1
) 中的行与右表 ( t2
) 中的任何行都不匹配,则LEFT JOIN
仍将两个表中的行列组合成新行,并将新行包含在结果行中。但是,它对右表中该行的所有列使用NULL
。
换句话说, LEFT JOIN
返回左表中的所有行,无论左表中的行是否具有右表中的匹配行。
如果没有匹配,则右表中的行的列将包含NULL
。
以下维恩图可帮助您直观地了解LEFT JOIN
子句的工作原理:

MySQL LEFT JOIN 子句示例
让我们举一些使用LEFT JOIN
子句的示例。
1)使用MySQL LEFT JOIN子句连接两个表
请参阅示例数据库中的下表customers
和orders
。

每个客户可以有零个或多个订单,而每个订单必须属于一个客户。
此查询使用LEFT JOIN
子句来查找所有客户及其订单:
SELECT
customers.customerNumber,
customerName,
orderNumber,
status
FROM
customers
LEFT JOIN orders ON
orders.customerNumber = customers.customerNumber;
Code language: SQL (Structured Query Language) (sql)
或者,您可以使用表别名来节省一些输入:
SELECT
c.customerNumber,
customerName,
orderNumber,
status
FROM
customers c
LEFT JOIN orders o
ON c.customerNumber = o.customerNumber;
Code language: SQL (Structured Query Language) (sql)

在这个例子中:
- 左表是
customers
,右表是orders
。 -
LEFT JOIN
子句返回所有客户,包括没有订单的客户。如果客户没有订单,则orderNumber
和status
列中的值为NULL
。
由于表 Customers 和 Orders 在使用 equal 运算符的连接条件中具有相同的列名 ( customerNumber
),因此您可以使用 USING 语法,如下所示:
SELECT
customerNumber,
customerName,
orderNumber,
status
FROM
customers
LEFT JOIN orders USING (customerNumber);
Code language: SQL (Structured Query Language) (sql)
以下子句是等效的:
USING (customerNumber)
Code language: SQL (Structured Query Language) (sql)
和
ON c.customerNumber = o.customerNumber
Code language: SQL (Structured Query Language) (sql)
如果将LEFT JOIN
子句替换为INNER JOIN
子句,您将获得唯一至少拥有一个订单的客户。
2)使用MySQL LEFT JOIN子句查找不匹配的行
当您想要查找一个表中没有另一个表中的匹配行的行时, LEFT JOIN
子句非常有用。
以下示例使用LEFT JOIN
查找没有订单的客户:
SELECT
c.customerNumber,
c.customerName,
o.orderNumber,
o.status
FROM
customers c
LEFT JOIN orders o
ON c.customerNumber = o.customerNumber
WHERE
orderNumber IS NULL;
Code language: SQL (Structured Query Language) (sql)

3)使用MySQL LEFT JOIN连接三个表
请参阅以下三个表employees
、 customers
和payments
:

此示例使用两个LEFT JOIN
子句来连接三个表: employees
、 customers
和payments
。
SELECT
lastName,
firstName,
customerName,
checkNumber,
amount
FROM
employees
LEFT JOIN customers ON
employeeNumber = salesRepEmployeeNumber
LEFT JOIN payments ON
payments.customerNumber = customers.customerNumber
ORDER BY
customerName,
checkNumber;
Code language: SQL (Structured Query Language) (sql)
这张图显示了部分输出:

怎么运行的。
- 第一个
LEFT JOIN
返回代表每个员工的所有员工和客户,如果该员工不负责任何客户,则返回NULL
。 - 第二个
LEFT JOIN
返回由员工代表的每个客户的付款,如果客户没有付款,则返回NULL
。
WHERE
子句中的条件与ON
子句中的条件
请参阅以下示例。
SELECT
o.orderNumber,
customerNumber,
productCode
FROM
orders o
LEFT JOIN orderDetails
USING (orderNumber)
WHERE
orderNumber = 10123;
Code language: SQL (Structured Query Language) (sql)
此示例使用LEFT JOIN
子句从表orders
和orderDetails
中查询数据。查询返回订单号10123
的订单及其行项。

但是,如果将条件从WHERE
子句移至ON
子句:
SELECT
o.orderNumber,
customerNumber,
productCode
FROM
orders o
LEFT JOIN orderDetails d
ON o.orderNumber = d.orderNumber AND
o.orderNumber = 10123;
Code language: SQL (Structured Query Language) (sql)
将会有不同的意义。
在这种情况下,查询返回所有订单,但只有订单10123
有与其关联的订单项,如下图所示:

请注意,对于INNER JOIN
子句, ON
子句中的条件与WHERE
子句中的条件等效。
在本教程中,您学习了如何使用 MySQL LEFT JOIN
子句连接两个或多个表中的数据。