inner join 和 outer join 的区别

本文详细介绍了SQL中的三种连接类型:内连接(inner join)、左外连接(left outer join)及全外连接(full outer join)。通过具体的示例,展示了如何使用这些连接来获取不同表之间的交集、并集及各自独有的数据。
部署运行你感兴趣的模型镜像

假设你要join两个没有重复列的表,这是最常见的情况:

  • inner join  A 和 B 获得的是A和B的交集(intersect),即韦恩图(venn diagram) 相交的部分.

  • outer join A和B获得的是A和B的并集(union), 即韦恩图(venn diagram)的所有部分.

    示例

    假定有两张表,每张表只有一列,列数据如下:

    A    B
    -    -
    1    3
    2    4
    3    5
    4    6

    注意(1,2)是A表独有的,(3,4) 两张共有, (5,6)是B独有的。

    Inner join

    使用等号进行inner join以获得两表的交集,即共有的行。

    select * from a INNER JOIN b on a.a = b.b;
    select a.*,b.*  from a,b where a.a = b.b;
    
    a | b
    --+--
    3 | 3
    4 | 4
    

    Left outer join

     left outer join 除了获得B表中符合条件的列外,还将获得A表所有的列。

    select * from a LEFT OUTER JOIN b on a.a = b.b;
    select a.*,b.*  from a,b where a.a = b.b(+);
    
    a |  b  
    --+-----
    1 | null
    2 | null
    3 |    3
    4 |    4
    

    Full outer join

    full outer join 得到A和B的交集,即A和B中所有的行.。如果A中的行在B中没有对应的部分,B的部分将是 null, 反之亦然。

    select * from a FULL OUTER JOIN b on a.a = b.b;
    
     a   |  b  
    -----+-----
       1 | null
       2 | null
       3 |    3
       4 |    4
    null |    6
    null |    5

本文由尤慕译自Stack Overflow,转载请保留此信息。


您可能感兴趣的与本文相关的镜像

Linly-Talker

Linly-Talker

AI应用

Linly-Talker是一款创新的数字人对话系统,它融合了最新的人工智能技术,包括大型语言模型(LLM)、自动语音识别(ASR)、文本到语音转换(TTS)和语音克隆技术

### SQL `INNER JOIN` vs `OUTER JOIN` 区别解释 #### 定义与功能差异 `INNER JOIN` 只返回两个表中满足连接条件的记录。这意味着只有当左表右表都存在匹配的数据时,才会显示这些数据[^1]。 相比之下,`OUTER JOIN` 则会返回即使在另一表中没有匹配也会返回的行。具体来说: - **LEFT JOIN (LEFT OUTER JOIN)**:返回左表中的所有记录以及右表中存在的匹配;如果右表中不存在,则结果集中相应的列为空(NULL)[^2]。 - **RIGHT JOIN (RIGHT OUTER JOIN)**:类似于 LEFT JOIN ,但是取的是右边表格的所有记录加上左边存在的对应部分。 - **FULL OUTER JOIN**:理论上应该返回两张表所有的组合情况,不过 MySQL 并不直接支持此语法,可以通过 UNION 左外连加右外连来实现相同效果。 #### 示例对比 假设有一个名为 `students` 的学生信息表另一个叫作 `courses` 的课程注册表,其中包含如下字段: - students(id, name) - courses(student_id, course_name) ##### 使用 `INNER JOIN` ```sql SELECT s.name AS student_name, c.course_name FROM students s INNER JOIN courses c ON s.id = c.student_id; ``` 这段代码只会显示出那些既存在于 `students` 表又存在于 `courses` 表的学生及其所选修的课程名称。 ##### 使用 `LEFT JOIN` ```sql SELECT s.name AS student_name, IFNULL(c.course_name,'未选课') as course_name FROM students s LEFT JOIN courses c ON s.id = c.student_id; ``` 这里不仅展示了已报名任何一门或多门课程的同学的信息,还包括了尚未选择任何课程的学生,并将其对应的课程名设为 "未选课"。 ##### 使用 `RIGHT JOIN` ```sql SELECT s.name AS student_name, c.course_name FROM students s RIGHT JOIN courses c ON s.id = c.student_id; ``` 这将展示所有已经选择了至少一节课的学生名单,同时也可能包括一些重复项或来自其他班级的学生(取决于实际数据结构),因为是从右侧表开始进行关联操作的结果集。 ##### 模拟 `FULL OUTER JOIN` 由于 MySQL 不原生提供 `FULL OUTER JOIN` 关键字的支持,可以采用以下方式模拟其行为: ```sql (SELECT s.name AS student_name, c.course_name FROM students s LEFT JOIN courses c ON s.id = c.student_id) UNION ALL (SELECT NULL ,c.course_name FROM courses c WHERE NOT EXISTS (SELECT * FROM students s WHERE s.id=c.student_id)); ``` 该语句先执行了一个左侧外部联接,再补充上仅存在于右侧表而不在左侧表内的条目,从而达到全外连接的效果。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值