MYSQL-175. 组合两个表
目录
题目链接:
题目:
解题思路:
代码:
总结:
题目链接:
175. 组合两个表 - 力扣(LeetCode)
题目:
175. 组合两个表
已解答
简单
相关标签
相关企业
SQL Schema
Pandas Schema
表: Person
+-------------+---------+ | 列名 | 类型 | +-------------+---------+ | PersonId | int | | FirstName | varchar | | LastName | varchar | +-------------+---------+ personId 是该表的主键(具有唯一值的列)。 该表包含一些人的 ID 和他们的姓和名的信息。
表: Address
+-------------+---------+ | 列名 | 类型 | +-------------+---------+ | AddressId | int | | PersonId | int | | City | varchar | | State | varchar | +-------------+---------+ addressId 是该表的主键(具有唯一值的列)。 该表的每一行都包含一个 ID = PersonId 的人的城市和州的信息。
编写解决方案,报告 Person
表中每个人的姓、名、城市和州。如果 personId
的地址不在 Address
表中,则报告为 null
。
以 任意顺序 返回结果表。
结果格式如下所示。
示例 1:
输入: Person表: +----------+----------+-----------+ | personId | lastName | firstName | +----------+----------+-----------+ | 1 | Wang | Allen | | 2 | Alice | Bob | +----------+----------+-----------+ Address表: +-----------+----------+---------------+------------+ | addressId | personId | city | state | +-----------+----------+---------------+------------+ | 1 | 2 | New York City | New York | | 2 | 3 | Leetcode | California | +-----------+----------+---------------+------------+ 输出: +-----------+----------+---------------+----------+ | firstName | lastName | city | state | +-----------+----------+---------------+----------+ | Allen | Wang | Null | Null | | Bob | Alice | New York City | New York | +-----------+----------+---------------+----------+ 解释: 地址表中没有 personId = 1 的地址,所以它们的城市和州返回 null。 addressId = 1 包含了 personId = 2 的地址信息。
面试中遇到过这道题?
1/5
是
否
通过次数
644,750/864.2K
通过率
74.6%
解题思路:
多表查询,只需要将Person当作左表 然后进行左连接两个表即可
代码:
# Write your MySQL query statement below
Select a.FirstName,a.LastName,b.City,b.State from Person a
left join Address b on a.PersonId=b.PersonId;
MySQL 查询语句详解:左连接查询个人与地址信息
一、语句功能概述
sql
SELECT a.FirstName, a.LastName, b.City, b.State
FROM Person a
LEFT JOIN Address b ON a.PersonId = b.PersonId;
这条 SQL 语句的核心功能是关联查询Person(个人信息表)和Address(地址表)的数据,最终返回 “个人姓名(名 + 姓)+ 所在城市 + 所在州” 的组合信息。采用LEFT JOIN(左连接)确保了即使某个人没有对应的地址信息,也会被保留在结果中,此时地址相关字段会显示NULL。
二、逐部分解析
1. SELECT 子句:指定返回字段
sql
SELECT a.FirstName, a.LastName, b.City, b.State
a.FirstName:表示从表Person(别名a)中获取 “名” 字段。
a.LastName:表示从表Person(别名a)中获取 “姓” 字段。
b.City:表示从表Address(别名b)中获取 “城市” 字段。
b.State:表示从表Address(别名b)中获取 “州 / 省份” 字段。
作用:明确查询结果需要包含哪些字段,避免使用SELECT *返回冗余数据,提高查询效率和结果可读性。
2. FROM 子句:指定主表及别名
sql
FROM Person a
Person是主表(左表),存储个人的基础信息(如姓名、ID 等)。
a是Person表的别名,用于简化后续语句中的表名引用(避免重复书写长表名)。
示例表结构(假设):
Person表可能包含以下字段:
PersonId FirstName LastName
1 John Doe
2 Jane Smith
3 Bob Brown
3. LEFT JOIN 子句:关联右表并指定连接条件
sql
LEFT JOIN Address b ON a.PersonId = b.PersonId
LEFT JOIN Address b:表示将左表Person与右表Address进行左连接,b是Address表的别名。
ON a.PersonId = b.PersonId:是连接条件,通过 “个人 ID”(PersonId)将两表关联 —— 即Person表中的PersonId与Address表中的PersonId相等的记录会被匹配到一起。
右表(Address)结构(假设):
AddressId PersonId City State
101 1 New York NY
102 2 London England
左连接逻辑:
左表(Person)的所有记录都会被保留在结果中。
右表(Address)只保留与左表PersonId匹配的记录;若左表某条记录在右表中无匹配(如PersonId=3的 Bob),则右表字段(City、State)显示NULL。
三、查询结果示例及分析
基于上述假设的表数据,查询结果如下:
FirstName LastName City State
John Doe New York NY
Jane Smith London England
Bob Brown NULL NULL
结果解读:
John(PersonId=1)在Address表中有匹配记录,因此City和State显示具体值。
Jane(PersonId=2)在Address表中有匹配记录,地址信息正常显示。
Bob(PersonId=3)在Address表中无对应地址(无PersonId=3的记录),因此City和State用NULL填充,但 Bob 的姓名信息仍被保留(左连接的核心特性)。
四、左连接与其他连接的对比
与 INNER JOIN(内连接)的区别:
若使用INNER JOIN,查询结果会只保留两表中都有匹配的记录,Bob(无地址)会被过滤掉。结果如下:
FirstName LastName City State
John Doe New York NY
Jane Smith London England
与 RIGHT JOIN(右连接)的区别:
若使用RIGHT JOIN,会保留右表(Address)的所有记录,即使某条地址记录在Person表中无匹配(如假设Address表有PersonId=4的地址,但Person表无此 ID),则左表字段会显示NULL。
五、应用场景与优势
适用场景:
需查询 “主表全部数据 + 从表关联数据” 的场景(如 “查询所有用户及其地址,包括没有填写地址的用户”)。
确保不丢失主表核心信息(如用户基本信息),同时补充关联的附加信息(如地址)。
优势:
完整性:保留左表所有记录,避免因从表无数据而丢失主表关键信息。
灵活性:通过NULL标识 “无关联数据”,清晰区分 “有数据但为空” 和 “无数据” 两种情况。
六、潜在问题与优化
避免笛卡尔积:
连接条件(ON a.PersonId = b.PersonId)是关键,若遗漏或错误,会导致两表所有记录交叉匹配(笛卡尔积),产生大量冗余数据。
处理NULL值:
结果中City或State为NULL时,可使用COALESCE函数替换为默认值(如 “未知城市”),例如:
sql
SELECT
a.FirstName,
a.LastName,
COALESCE(b.City, 'Unknown') AS City,
COALESCE(b.State, 'Unknown') AS State
FROM Person a
LEFT JOIN Address b ON a.PersonId = b.PersonId;
性能优化:
若表数据量大,需确保PersonId字段(连接条件)已建立索引,否则连接操作可能因全表扫描导致性能下降。
七、总结
这条左连接查询语句通过关联Person和Address表,既保证了所有个人信息不丢失,又能准确匹配对应的地址信息,是 “主从表关联查询” 的典型应用。理解左连接的逻辑(保留左表、匹配右表、无匹配补NULL),对于处理 “核心数据 + 可选关联数据” 的场景至关重要,也是 MySQL 查询的基础知识点。
总结:
该SQL查询通过左连接(LEFT JOIN)关联Person和Address表,获取每个人的姓名及对应地址信息。关键点:1) 使用Person作为左表确保所有人都会被返回;2) 当Address表中无匹配记录时,地址字段显示为NULL;3) 通过PersonId字段关联两表。这种查询方式适用于需要获取主表全部记录及关联表匹配数据的场景,是处理"核心数据+可选关联信息"的典型解决方案。