MySQL其他

本文最后更新于:2022年7月11日 晚上

概览:MySQL联表查询,in与exist

联表查询

官方链接:MySQL :: MySQL 5.7 参考手册 :: 8.2.1.6 嵌套循环连接算法

嵌套链接查询:一次一个地从循环中地第一个表中读取行,并将行传递给下一个循环。

eg: t1 t2 t3

1
2
3
4
Table   Join Type
t1 range
t2 ref
t3 ALL

查询

1
2
3
4
5
6
7
for each row in t1 matching range {
for each row in t2 matching reference key {
for each row in t3 {
if row satisfies join conditions, send to client
}
}
}

块嵌套循环连接

使用在外部循环中读取的行的缓冲来减少读取内部循环中表的次数。

即将外部循环读取10行,然后在内部循环中读取的一行都与这10行做比较。

MySQL连接

内连接:表1 inner join 表2(取表1和表2相交部分),只返回相匹配的结果。

左外连接:表1 left join 表2 on 表1.字段=表2.字段 (以表1为准,表2进行匹配),不管是否匹配都会以表1的条数返回结果,没有匹配条件的数据显示null

右外连接:表1 right join 表2 on 表1.字段=表2.字段 (以表2为准,表1进行匹配)

全连接:表1 union all 表2 (表1 和表2的列数必须一样多,union 去除重复项,union all 不剔除重复项)

外连接:表1 full outer join 表2 (取表1和表2不相交的部分)

ps:MYSQL 不支持外连接,可以用左右连接后再全连接代替

参考链接:https://blog.csdn.net/weixin_41381863/article/details/88560503

in与exist

exists对外表用loop逐条查询,每次查询都会查看exists的条件语句,当exists里的条件语句能够返回记录行时(无论记录行是的多少,只要能返回),条件就为真,返回当前loop到的这条记录;反之,如果exists里的条件语句不能返回记录行,则当前loop到的这条记录被丢弃,exists的条件就像一个bool条件,当能返回结果集则为true,不能返回结果集则为false

  • 总结:如果A表有n条记录,那么exists查询就是将这n条记录逐条取出,然后判断n遍exists条件。

in查询相当于多个or条件的叠加。

  • 总结:in查询就是先将子查询条件的记录全都查出来,假设结果集为B,共有m条记录,然后再将子查询条件的结果集分解成m个,再进行m次查询。

使用上:in查询的子条件返回结果必须只能有一个字段,但是exists就没有这个限制。

1)IN查询在内部表和外部表上都可以使用到索引。
2)Exists查询仅在内部表上可以使用到索引。
3)当子查询结果集很大,而外部表较小的时候,Exists的Block Nested Loop(Block 嵌套循环)的作用开始显现,并弥补外部表无法用到索引的缺陷,查询效率会优于IN。
4)当子查询结果集较小,而外部表很大的时候,Exists的Block嵌套循环优化效果不明显,IN 的外表索引优势占主要作用,此时IN的查询效率会优于Exists。
5)表的规模不是看内部表和外部表,而是外部表和子查询结果集。

参考链接:https://blog.csdn.net/jinjiniao1/article/details/92666614

where having区别

where是在分组前对数据进行过滤, —— 表数据过滤,在分组聚合之前对真实表数据过滤,

而having是在分组后对数据进行过滤,—— 组数据过滤,在分组聚合之后对数据过滤,having里可以使用聚合函数

执行顺序上:where > 聚合函数 > having

参考链接:https://blog.csdn.net/qq_37189082/article/details/122607549


本博客所有文章除特别声明外,均采用 CC BY-SA 4.0 协议 ,转载请注明出处!