田超凡
1 临时表概念
MySQL临时表在很多场景中都会用到,比如用户自己创建的临时表用于【保存临时数据】,以及MySQL内部在执行【复杂SQL】时,需要借助临时表进行【分组、排序、去重】等操作,临时表具有一下几个特点:
(1)临时表不能通过show tables查看,在服务器重启之后,所有的临时表将全部被销毁。
(2)临时表是每个进程独享的,当前进程(客户端)创建的临时表,其他进程(客户端)是查不到临时表里面的数据的,所以不同客户端可以创建同名的临时表。
2 临时表分类
(1)外部临时表
通过create temporary table语句创建的临时表为外部临时表
(2)内部临时表
用来存储某些操作的【中间结果】,这些操作可能包括在【优化阶段】或者【执行阶段】,这种内部表对用户来说是不可见的。通常在执行复杂SQL语句时,比如group by,distinct,union等语句时,MySQL内部将使用【自动生成的临时表】,以辅助SQL的执行。我们可以使用执行计划查看,如果一条sql语句的执行计划中【列extra】结果为Using temporary,那么也就说明这个查询要使用到临时表。
3 group by执行流程
(1)创建一个内部临时表,有两列,一列是age,一列是count(*)。
(2)全表扫描【原始表】(聚簇索引会在后边的内容讲解),每扫描一条数据进行一次判断,第一种情况,这条数据的年龄在临时表中不存在,则将年龄填入,count列填1。第二种情况,该条数据在临时表中存在,则将count列加1。临时表的存在是为了辅助计算。
(3)对临时表的数据按照年龄进行排序。
4 内部临时表创建时机
MySQL在以下几种情况会创建临时表:
(1)使用GROUP BY分组,且分组字段没有索引时。
(2)使用DISTINCT查询。
(3)使用UNION进行结果合并,辅助去重。(【union all】不会使用零时表,因为他不需要去重)
5 其他临时表
其实临时表还可以分为【内存临时表】和【磁盘临时表】。内存临时表使用memery引擎(Memory引擎不支持BOLB和TEXT类型),磁盘临时表默认使用innodb引擎。在以下几种情况下,会创建磁盘临时表:
1、数据表中包含BLOB/TEXT列;
2、在 GROUP BY 或者 DSTINCT 的列中有超过 512字符的字符类型列;
3、在SELECT、UNION、UNION ALL查询中,存在最大长度超过512的列(对于字符串类型是512个字符,对于二进制类型则是512字节);