【MySQL】多表查询(四)

news2024/11/28 22:54:38

🚗MySQL学习·第四站~
🚩本文已收录至专栏:MySQL通关路
❤️文末附全文思维导图,感谢各位点赞收藏支持~

之前我们介绍DQL语句,也就是数据查询语句的时候,介绍的查询操作都是单表查询,他的功能当然不仅局限于此,我们还可以一次性对多个表的数据进行查询操作,也就是接下来要介绍的多表查询。

一.多表关系

在我们的项目开发中,在进行数据库表结构设计时,会根据业务需求及业务模块之间的关系,分析并设计表结构,由于业务之间经常会存在相互关联关系,所以由此设计出的各个表结构之间也存在着各种联系,基本上分为三种:

  • 一对多(多对一)
  • 多对多
  • 一对一

(1) 一对多

  • 业务示例: 部门与员工的关系
  • 关系介绍: 一个部门对应多个员工,一个员工对应一个部门
  • 实现方式: 我们通常会在 ‘多’ 的一方建立外键,指向 ‘一’ 的一方的主键

在这里插入图片描述

(2) 多对多

  • 业务示例: 学生与课程的关系
  • 关系介绍: 一个学生可以选修多门课程,一门课程也可以供多个学生选择
  • 实现方式: 建立第三张中间表,中间表至少包含两个外键,分别关联两方主键

在这里插入图片描述

(3) 一对一

  • 业务示例: 用户与用户详情的关系
  • 关系介绍: 一对一关系,多用于单表拆分,将一张表的基础字段放在一张表中,其他详情字段放在另 一张表中,以提升操作效率
  • 实现方式: 在任意一方加入外键,关联另外一方的主键,并且设置外键为唯一的(UNIQUE)

在这里插入图片描述

二.多表查询

(1) 引入

多表查询就是指一次性从多张表中查询数据。

原来我们查询单表数据,执行的SQL形式为:select 字段列表 from 表名;

现在我们想要执行多表查询,就只需要使用逗号分隔多张表即可,如: select 字段列表 from 表名1, 表名2;

但是我们这样使用却发现存在问题:的确同时查到了多张表的数据,但是数据形式和我们想要的并不一样,它排列组合了两张表中的所有数据项!

在这里插入图片描述

例如我们查询员工、部门表,本来我们预期是每个员工对应其所在的部门,但事实确实,每个员工都对应了所有部门。这种现象也称之为 笛卡尔积
在这里插入图片描述

因此,在多表查询中,我们需要根据业务情况进行连接查询,消除无效的笛卡尔积,只保留两张表关联部分的有效数据。

例如在上述示例,我们通过表名.字段名指定员工表的外键等于部门表的主键即可获得预期数据~

在这里插入图片描述

特别说明

  • 我们不光可以为字段起别名,同样可以使用相同的语法给表起别名,table as 别名或table 别名
  • 一旦为表起了别名,就不能再使用表名来指定对应的字段了,此时只能够使用别名来指定字 段
  • 在获取表字段时,我们可以使用表名.字段名来进行指定。

(2) 内连接

内连接查询的是两张表交集部分的数据(也就是绿色部分的数据)。语法分为两种: 隐式内连接、显式内连接。
在这里插入图片描述

(2.1) 隐式内连接

  • 语法
SELECT 字段列表 FROM1,2 WHERE 限制条件;
  • 示例
# 查询每一个员工的姓名 , 及关联的部门的名称 
select e.name,d.name from emp e,dept d where e.dept_id = d.id;

在这里插入图片描述

(2.2) 显式外连接

  • 语法
SELECT 字段列表 FROM1 [ INNER ] JOIN2 ON 连接条件 ... ;
  • 示例(与上述相同)
# 查询每一个员工的姓名 , 及关联的部门的名称 
select e.name, d.name from emp e inner join dept d on e.dept_id = d.id;

在这里插入图片描述

(3) 外连接

外连接分为:左外连接 和 右外连接。左外连接相当于查询表1(左表)的所有数据,当然也包含表1和表2交集部分的数据。右外连接相当于查询表2(右表)的所有数据,当然也包含表1和表2交集部分的数据。

在这里插入图片描述

(3.1) 左外连接

  • 语法
SELECT 字段列表 FROM1 LEFT [ OUTER ] JOIN2 ON 条件 ... ;
  • 示例:
# 查询emp表的所有数据, 和对应的部门信息
select e.*, d.name from emp e left outer join dept d on e.dept_id = d.id;

在这里插入图片描述

不仔细看会觉得和内连接没啥区别,但是仔细看会发现我们null数据也能够正常显示出来,而内连接则无法查询到null,这是因为我们外连接会获取到一张表的全部数据,而内连接只获取交集部分数据。

(3.2) 右外连接

  • 语法
SELECT 字段列表 FROM1 RIGHT [ OUTER ] JOIN2 ON 条件 ... ;
  • 示例
# 查询emp表的所有数据, 和对应的部门信息 
select e.*, d.name from emp e left outer join dept d on e.dept_id = d.id;

在这里插入图片描述

这么一看感觉左右外连接查询结果都差不多,确实如此,通常左外连接和右外连接是可以相互替换的,只需要调整在连接查询时SQL中,表结构的先后顺序就可以了。而我们在日常开发使用时,更偏向于左外连接。

(4) 自连接

自连接查询,顾名思义,就是自己连接自己,也就是把一张表进行连接查询多次。需要注意的是在自连接查询中,必须要为表起别名,要不然我们不清楚所指定的条件、返回的字段,到底是哪一张表的字段。

  • 自连接查询,可以是内连接查询,也可以是外连接查询,其关键点在于 自己连接自己
SELECT 字段列表 FROM 表A 别名A JOIN 表A 别名B ON 条件 ... ;
  • 示例
# 查询员工 及其 所属领导的名字,如果员工没有领导, 也需要查询出来
select a.name '员工', b.name '领导' from emp a left join emp b on a.managerid = 
b.id;

在这里插入图片描述

(5) 联合查询

对于联合查询,就是把多次查询的结果合并起来,形成一个新的查询结果集。

  • 语法说明
SELECT 字段列表 FROM 表A  ...   # 查询结果集1
UNION [ ALL ]
SELECT 字段列表 FROM 表B  ....;  # 查询结果集2
  • 注意事项

    • 对于联合查询的多张表的字段列表必须保持一致字段类型也需要保持一致,如果不一致将会报错。

    • union all 会将全部的数据直接合并在一起,union 会对合并之后的数据去重

  • 示例代码

select * from emp where salary < 5000
union all
select * from emp where age > 50;

在这里插入图片描述

union all查询出来的结果,仅仅只对数据集进行简单的合并,查询结果中可能会存在重复数据项,使用union即可去除重复数据项。

(6) 子查询

(6.1) 介绍

SQL语句中嵌套SELECT语句,称为嵌套查询,又称子查询。

# 示例语法
SELECT * FROM t1 WHERE column1 = (SELECT column1 FROM t2); 

子查询外部的语句可以是INSERT / UPDATE / DELETE / SELECT 的任何一个。嵌套SELECT语句可以位于SELECT之后FROM之后WHERE之后

  • 子查询根据结果不同,分为:
    • 标量子查询(子查询结果为单个值
    • 子查询 (子查询结果为一列)
    • 子查询 (子查询结果为一行)
    • 子查询 (子查询结果为多行多列)

(6.2) 标量子查询

子查询返回的结果是单个值(例如数字、字符串、日期等)。 常用的操作符有:= <> > >= < <=

  • 使用示例:查询 “销售部” 的所有员工信息
# 拆分1: 查询 "销售部" 部门ID,返回单个id值
select id from dept where name = '销售部';

# 拆分2:根据部门ID, 查询员工信息
select id from dept where name = xxx;

# 完整版
 select * from emp where dept_id = (select id from dept where name = '销售部');

在这里插入图片描述

(6.3) 列子查询

子查询返回的结果是一列(可以是多行)。常用的操作符:IN 、NOT IN 、 ANY 、SOME 、 ALL

  • 使用示例:查询比 财务部 所有人工资都高的员工信息
# 拆分1: 查询财务部id
select id from dept where name = '财务部';

# 拆分2: 查询财务部员工工资
select salary from emp where dept_id = 拆分1;
select salary from emp where dept_id = (select id from dept where name = '财务部');

#  拆分3 : 比 财务部 所有人工资都高的员工信息
select * from emp where salary > all (拆分2);

# 合并
select * from emp where salary > all ( select salary from emp where dept_id = 
(select id from dept where name = '财务部') );

在这里插入图片描述

(6.4) 行子查询

子查询返回的结果是一行(可以是多列)。常用的操作符:= 、<> 、IN 、NOT IN

  • 使用示例:查询与 “张无忌” 的薪资及直属领导相同的员工信息 ;
# 拆分1:查询 "张无忌" 的薪资及直属领导
select salary, managerid from emp where name = '张无忌';

# 拆分2:查询与 "张无忌" 的薪资及直属领导相同的员工信息
select * from emp where (salary,managerid) = (xx,xx);

# 合并
select * from emp where (salary,managerid) = (select salary, managerid from emp 
where name = '张无忌');

在这里插入图片描述

(6.5) 表子查询

子查询返回的结果是多行多列。常用的操作符:IN

  • 使用示例:查询与 “鹿杖客” , “宋远桥” 的职位和薪资相同的员工信息
# 拆分1:查询 "鹿杖客" , "宋远桥" 的职位和薪资
select job, salary from emp where name = '鹿杖客' or name = '宋远桥';

# 拆分2:查询与 "鹿杖客" , "宋远桥" 的职位和薪资相同的员工信息
select * from emp where (job,salary) in ( xxx );

 # 合并
 select * from emp where (job,salary) in (select job, salary from emp where name = '鹿杖客' or name = '宋远桥');

最后值得一提是:多表查询业务能实现相关需求的SQL往往会很多, 写法也多种多样,总之,能满足我们的需求,查询出符合条件的记录即可~

三.全文概览

在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/769191.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

山西电力市场日前价格预测【2023-07-20】

日前价格预测 预测明日&#xff08;2023-07-20&#xff09;山西电力市场全天平均日前电价为337.62元/MWh。其中&#xff0c;最高日前电价为375.88元/MWh&#xff0c;预计出现在06: 00。最低日前电价为291.47元/MWh&#xff0c;预计出现在13: 30。 价差方向预测 1&#xff1a;实…

Elasticsearch 介绍及java集成

一、Elasticsearch 基础介绍 ElasticSearch 是分布式实时搜索、实时分析、实时存储引擎&#xff0c;简称&#xff08;ES)&#xff0c; 成立于2012年&#xff0c;是一家来自荷兰的、开源的大数据搜索、分析服务提供商&#xff0c;为企业提供实时搜索、数据分析服务&#xff0c;…

Django MultiValueDictKeyError 表单数据用request.POST 非表单数据用request.body

表单数据&#xff1a;Content-Type(请求头)为application/x-www-form-urlencoded的数据。 用request.POST获取 a request.POST.get(a) a request.POST[a] alist request.POST.getlist(a) 非表单数据&#xff1a;Content-Type(请求头)为非application/x-www-form-urlenco…

ORACLE TO POSTGRESQL 来自2天上海的印象

开头还是介绍一下群&#xff0c;如果感兴趣polardb ,mongodb ,mysql ,postgresql ,redis 等有问题&#xff0c;有需求都可以加群群内有各大数据库行业大咖&#xff0c;CTO&#xff0c;可以解决你的问题。加群请联系 liuaustin3 &#xff0c;在新加的朋友会分到2群&#xff08;共…

Qt MenuBar自定义Icon大小

提到QMenu中如何定制Icon的大小&#xff0c;第一个想到的是使用qss来修改样式&#xff0c;便尝试了如下语句&#xff1a; QMenu::icon { width: 24px;height: 24px; } 但是经尝试&#xff0c;这个办法并未奏效&#xff0c;QMenu中图标大小&#xff0c;默认为16*16&#xff0c…

一篇文章教会你,在IntelliJ IDEA 中,一些让你相见恨晚的技巧

1.Easy Code Easy Code我个人在写博客案例demo时用的比较多&#xff0c;它可以快速的将数据库表映射成Java中的entity、controller、service、dao、mapper等文件&#xff0c;少量编码实现快速开发。 先用database连接数据库&#xff0c;在对应表上直接右键执行EasyCode即可生成…

计算机服务器中了360后缀勒索病毒,正确的解密恢复数据库的方式有哪些

随着计算机技术的不断发展&#xff0c;网络安全也引起了人们重视&#xff0c;近期&#xff0c;我们收到很多企业的求助&#xff0c;企业的计算机服务器被360后缀勒索病毒攻击&#xff0c;导致系统内的数据库全部被加密&#xff0c;重要数据无法被读取&#xff0c;严重影响了企业…

你认为大数据的特点是什么?_光点科技

随着信息技术的迅猛发展&#xff0c;大数据已成为当今社会不可忽视的重要资源。它是指规模庞大且快速增长的数据集合&#xff0c;其中包含着宝贵的信息和见解。大数据的特点是多样而复杂的&#xff0c;它们塑造了我们的世界并深刻地影响着各行各业。 巨大的规模&#xff1a;大数…

电脑pdf怎么免费转换成ppt?分享3个好方法!

在现代办公环境中&#xff0c;将PDF文件转换为PPT格式是一项常见的任务。在本文中&#xff0c;我们将分享三种免费的方法&#xff0c;帮助您将电脑上的PDF文件快速转换为PPT&#xff0c;以便更方便地编辑和展示。 方法一&#xff1a;使用Adobe Acrobat Reader DC Adobe Acrob…

Java File类的基本使用方法总结

Java File类的基本使用方法总结 java IO中File的使用是比较频繁的&#xff0c;在文件的上传和删除中都会用到的。比如我们在写管理系统的时候有可能会用到图片的上传&#xff0c;和删除。那么我们就会用到Java的 File来处理。 Java中File的基本使用创建和删除文件&#xff1a;…

剑指29.顺时针打印矩阵 31 栈的压入,弹出序列 03 数组中的重复数字 53缺失的数字 04二维数组中的查找

class Solution { public:vector<int> spiralOrder(vector<vector<int>>& matrix) { if (matrix.size() 0 || matrix[0].size() 0&#xff09; return {};//必须要写到最前面&#xff0c;因为right和bottom-1就是负数了vector<int> result;int l…

STM32开发踩坑——MDK如何生成bin文件

成立这个专栏的目的是&#xff0c;记录自己嵌入式开发遇到的问题&#xff0c;与成功的解决方法&#xff0c;方便自己回顾。 首先介绍下bin文件与hex文件的区别吧&#xff0c; 自己的理解&#xff1a; bin文件&#xff1a;纯粹的二进制&#xff08;0与1&#xff09;文件&…

防范运维端数据安全风险,数据库防水坝在不同行业的落地实践

在历史长河中&#xff0c;充满着强者未屈服于外部危险&#xff0c;却折戟内部威胁的记载&#xff0c;人类总是容易被咄咄逼人的外部所迷惑&#xff0c;反而忽略了近在咫尺的涌动暗潮。 数据安全领域&#xff0c;也面临类似的问题&#xff01; 数据库运维场景&#xff0c;数据安…

Linux 学习记录52(ARM篇)

Linux 学习记录52(ARM篇) 本文目录 Linux 学习记录52(ARM篇)一、汇编语言相关语法1. 汇编语言的组成部分2. 汇编指令的类型3. 汇编指令的使用格式 二、基本数据处理指令1. 数据搬移指令(1. 格式(2. 指令码类型(3. 使用示例 2. 立即数(1. 一条指令的组成 3. 移位操作指令(1. 格式…

MySQL执行过程与bufferPool缓存机制

MySQL执行过程与bufferPool缓存机制 一、SQL执行流程图二、个人理解的Innodb执行引擎执行顺序1、去磁盘文件查找id为1的整页数据&#xff0c;加载到Buffer Pool缓存池中&#xff1b;2、然后写入更新数据的旧值&#xff08;这里指namezhuge的数据&#xff09;&#xff0c;写入到…

【电路原理学习笔记】第4章:能量与功率:4.5 稳压电源与电池

第4章&#xff1a;能量与功率 4.5 稳压电源与电池 电网采用交流电形式将电能从发电站传输给用户&#xff0c;这是因为交流电易于转换成适宜传输的高压和终端用户使用的低压。在远距离传输时&#xff0c;采用高电压传输的效率和效益要高得多。对于给定的功率&#xff0c;较高的…

安全开发-PHP应用模版引用Smarty渲染MVC模型数据联动RCE安全TP框架路由访问对象操作内置过滤绕过核心漏洞

文章目录 自写模版引用Smarty模版引用代码RCE安全测试TP框架-开发-配置架构&路由&MVC模型TP框架-安全-不安全写法&版本过滤绕过 自写模版引用 1、页面显示样式编排 <?php include config.php; $templatefile_get_contents(new.html);$id$_GET[id] ? :1; $sq…

win11中的pagefile.sys

在C盘系统下&#xff0c;有一个命名为pagefile.sys的文件占用C盘太大的空间&#xff0c;不少用户怕删除pagefile.sys文件之后会对系统造成影响&#xff0c;而不少用户想要将pagefile.sys文件移动到D盘中。那么pagefile.sys是什么文件&#xff1f;Win10系统下pagefile.sys文件太…

解决appium-doctor报 bundletool.jar cannot be found

一、下载bundletool.jar 下载地址&#xff1a;https://github.com/google/bundletool/releases 二、重命名 重命名这个jar包为bundletool.jar&#xff0c;在android sdk目录下&#xff0c;新建bundle-tool目录&#xff0c;把bundletool.jar包放入其中。 三、配置环境 path后追加…

大模型开发(七):LLM提示工程(Prompt)与思维链(CoT)

全文共6500余字&#xff0c;预计阅读时间约13~20分钟 | 满满干货(附案例)&#xff0c;建议收藏&#xff01; 一、LLM模型的涌现能力 在GPT没有爆火之前&#xff0c;一直以来的共识都是&#xff1a;模型的规模越大&#xff0c;模型在下游任务上的能力越多、越强。 LLM原始训…