SQL 优化工具使用之 explain 详解
一、导读
对于大部分开发人员来说,平常接触的无非就是增删改查这些基本操作,创建存储过程,视图等等都是 DBA 该干的活,但是想要把这些基本操作写的近乎完美也是一件难事。
而 explain 显示了 MySQL 如何使用索引来处理 select 语句以及连接表。可以通过模拟 mysql 的优化器帮助选择更好的索引和写出更优化的查询语句。
二、explain 能干什么
- 表的读取顺序
- 数据读取操作的操作类型
- 哪些索引可以使用
- 哪些索引被实际使用
- 表之间的引用
- 每张表有多少行被优化器查询
说了这么多使用 explain 的好处,那么实际上到底该怎么玩? 答案: explain + 待执行的sql

从上表中我们看到,通过 explain+sql 执行后,显示了一张列表,那么接下来我们就详细说说这个个列表中各个字段的意思,只有先明确了各个字段的意思,才能知道 sql 的优劣程度。
三、explain 结果解释
id
决定表的读取顺序。
执行 select 语句查询的序列号,包含一组数字,表示查询中执行 select 子句或操作表的顺序
它有三种情况:
1、id相同,执行顺序由上至下;
2、id不同,如果是子查询,id的序号会递增,id值越大优先级越高,越先被执行;
3、id相同与不同,同时存在,如果 id 相同,可以认为是一组,从上往下顺序执行,在所有组中,id值越大,优先级越高,越先执行;
select_type
查询的类型,也就是数据读取操作的操作类型。他一共包含以下几种类型。
simple:简单的 select 查询,查询中不包含子查询或者 union;
primary:查询中若包含任何复杂的子查询,最外层查询则被标记;
subquery:在 select 或者 where 列表中包含了子查询;
derived:在 from 列表中包含的子查询被标记为 DERIVED(衍生表),mysql 会递归执行这些子查询,把结果放临时表中;
union:若第二个 select 出现在 union 之后,则被标记为 union,若 union 包含在 from 子句的子查询中,外层 select 将被标记为 DERIVED;
union result:从 union 表(即 union 合并的结果集)中获取 select 查询的结果;
type
访问类型,一个 sql 性能的重要指标
显示查询使用了何种类型,从最好到最差依次是 system > const > eq_ref > ref > range > index > all
system:表只有一行记录(等于系统表),这是 const 类型的特例,平时不会出现,这个也可忽略不计;
const:表示通过索引一次就找到了,const 用于比较 primary key 或者 unique 索引。因为只匹配一行记录,所以很快。如果将主键置于 where 列表中,mysql 就能将该查询转换成一个常量;
eq_ref:唯一性索引扫描,对于每一个索引键,表中只有一条记录与之匹配,常用于主键或唯一索引扫描;
ref:非唯一性索引扫描,返回匹配某个单独值得所有行,本质上也是一种索引访问,它返回所有匹配某个单独值的行,然而,它可能会找到多个符合条件的行,所以它应该属于查找和扫描的混合体;
range:只检索给定范围的行,使用一个索引来选择行,key 列显示使用哪个索引,一般就是在你的 where 语句中出现了 between、in 等的查询;这种范围索引扫描比全表扫描要好,因为它只需要开始于索引的某一个点,结束于另一个点,不用扫描全部索引;
index:index 于 all 区别为 index 类型只遍历索引树,这通常比 all 快,因为索引文件通常比数据文件小。也就是说虽然 all 和 index 都是读写表,但 index 是从索引中读取的,而 all 是从硬盘中读的;
all:也就是全表扫描;
备注:一般来说,得保证查询至少达到 range 级别,最好能达到ref。
possible_keys
显示可能会被应用到这张表的索引,一个或者多个。查询涉及到的字段上若存在索引,则该索引将被列出,但不一定被查询实际使用到。
key
实际使用到的索引。如果为 null,则没有使用索引。查询中若使用了覆盖索引,则该索引仅出现在key 列表中。
key_len
表示索引中使用的字节数,可通过该列计算查询中使用的索引的长度,在不损失精确性的情况下,长度越短越好。 key_len 显示的值为索引字段的最大可能长度,并非实际使用长度,即 key_len 是根据表定义计算而得,不是通过表内检索出的。
ref
显示索引的哪一列被使用了,如果可能的话,是一个常数,哪些列或常量别用于查找索引列上的值。
rows
根据表统计信息及索引选用情况,大致估算出找到所需的记录所需要读取的行数。
Extra
包含不适合在其它列中显示但十分重要的额外信息。
1、using filesort (出现这个东西不好):说明 mysql 会对数据使用一个外部的索引排序,而不是按照表内的索引顺序进行读取,mysql 中无法利用索引完成的排序操作称为"文件排序"。


2、using temporary(出现这个东西更不好,使用到了临时表):使用了临时表保存中间结果,Mysq 在对查询结果排序时使用临时表,常见于排序 order by 和分组查询 group by。

3、using index:表示相应的 select 操作中使用了覆盖索引(Covering Index),避免了访问了表的数据行,效率不错!
如果同时出现 using where,表明索引被用来执行索引键值的查找。

如果没有同时出现 using where,表明索引用来读取数据而非执行查找操作
- using where:使用了where
- impossible where:where 子句的值总是false,不能用来获取任何元素;
- select tables optimized away:在没有group by子句的情况下,基于索引优化MIN/MAX操作或者对于MyISAM存储引擎优化count(*)操作,不必等到执行阶段再进行计算,查询执行计划生成的阶段即完成优化;
- distinct
三、覆盖索引
理解方式一
就是 select 的数据列只用从索引列中就能取得,不必读取数据行,Mysql 可以利用索引返回 select列表中的字段,而不必根据索引再次读取数据文件,换句话说查询列要被所建的索引列覆盖。
理解方式二
索引是高效找到行的一个方法,但是一般数据库也能使用索引找到一个列的数据,因此它不必读取整个行,毕竟索引的叶子节点存储了索引数据。当能通过读取索引就可以得到想要的数据,那就不需要读取行了。一个索引包含了(或者覆盖了)满足查询结果的数据就叫做覆盖索引。
注意
如果要使用覆盖索引,一定要注意 select 列表中只取出需要的列,不可 select *,因为如果将所有的字段一起做索引会导致索引文件过大,查询性能下降。
相关文章:
SQL 优化工具使用之 explain 详解
一、导读 对于大部分开发人员来说,平常接触的无非就是增删改查这些基本操作,创建存储过程,视图等等都是 DBA 该干的活,但是想要把这些基本操作写的近乎完美也是一件难事。 而 explain 显示了 MySQL 如何使用索引来处理 select 语…...
深度解析Unity3D渲染管线:网格、材质与GPU渲染的协同逻辑
在3D实时渲染领域,网格(Mesh)、材质(Material)和GPU渲染三者构成了虚拟世界的基石。它们如同乐高积木的零件,通过精确的协作,最终在屏幕上呈现出复杂的视觉场景。本文将从技术原理、协作机制到性…...
POI优化Excel录入
57000单词原始录入时间258S 核心代码: List<Word> wordBookList ExcelUtil.getReader(file.getInputStream()).readAll(Word.class);if (!CollectionUtil.isEmpty(wordBookList)) {for (Word word : wordBookList) {//逐条向数据库中插入单词wordMapper.insert(word);}…...
实时图像与视频超分辨率:高效子像素卷积网络(ESPCN)解析
文章目录 概要理论知识操作实操环境配置基础命令格式:效果示例 概要 超分辨率系列论文阅读卷1:Real-Time Single Image and Video Super-Resolution Using an Efficient Sub-Pixel Convolutional Neural Network PDF网址:https://arxiv.org/…...
QT--对话框的切换
文章目录 前言一、主窗口ui二、创建子窗口三、步骤1.主界面------>子页面2.子界面------>主页面 四、总结 前言 之前我们学了qt中最重要的东西–信号和槽 我们现在实现这样一个demo,程序启动后弹出主界面,点击主界面的按钮弹出子窗口,…...
深入浅出:CUDA是什么,如何利用它进行高效并行计算
在当今这个数据驱动的时代,计算能力的需求日益增加,特别是在深度学习、科学计算和图像处理等领域。为了满足这些需求,NVIDIA推出了CUDA(Compute Unified Device Architecture),这是一种并行计算平台和编程模…...
Zotero PDF Translate插件配置百度翻译api
Zotero PDF Translate插件可以使用几种翻译api,虽然谷歌最好用,但是由于众所周知的原因,不稳定。而cnki有字数限制,有道有时也不行。其他的翻译需要申请密钥。本文以百度为例,进行申请 官方有申请教程: Zot…...
利用acme.sh 申请 Google 免费证书
1.Google API权限准备 获取 EAB 密钥 ID 和 HMAC 登录你的 GCP 控制台面板,进入 Public Certificate Authority API 管理页面(https://console.cloud.google.com/apis/library/publicca.googleapis.com)点击启动: 或者直接在下一…...
腾讯云cloudstudio使用笔记(一)
0、计划及目标 1)、这个系列用于将cloudstudio快速入门将前端代码在cloudstudio中从git仓库拉下来并运行—本文档的目标已实现 2)、基于cloudstudio和腾讯的ai代码助手腾讯自己满血的deepseek写代码,减少前端工作量—待补充 3)、…...
python自动化制作常规的日报数据可视化
python自动化制作常规的日报数据可视化 作者:i阿极 作者简介:Python领域新星作者、多项比赛获奖者:博主个人首页 😊😊😊如果觉得文章不错或能帮助到你学习,可以点赞👍收藏Ǵ…...
C语言:在主函数中输入十个等长的字符串。用另一函数对它们排序,然后在主函数输出这10个已排好序的字符串。
(1)用字符型二维数组 #include <stdio.h> #include <string.h> int main() {void sort(char s[][6]);int i;char str[10][6];printf("input 10 strings:\n");for (i0;i<10;i)scanf("%s",str[i]);sort(str);printf(&…...
构建高效智能对话前端:基于Ant Design X 的deepseek对话应用
文章目录 实现的效果前言Ant Design X添加欢迎组件创建对话气泡存储对话历史渲染对话气泡 输入组件WebSocket 连接总结 实现的效果 待机页面: 等待页面: 完成页面: 前言 随着人工智能技术的飞速发展,大模型对话系统已成为…...
SQLMesh 系列教程5- 详解SQL模型
本文将详细介绍 SQLMesh 的 SQL 模型组成要素及其在实际项目中的应用。SQLMesh 是一个强大的数据工程工具,其 SQL 模型由 MODEL DDL、预处理语句、主查询、后处理语句以及可选的 ON VIRTUAL UPDATE 语句组成。我们将通过一个电商平台每日销售报告的实例,…...
本地DeepSeek模型GGUF文件转换为PyTorch格式
接前文,我们在本地Windows系统上,基于GGUF文件部署了DeepSeek模型(DeepSeek-R1-Distill-Qwen-1.5B.gguf版本),但是GGUF是已经量化的版本,我们除了对其进行微调之外,无法对其训练,那么还有没有其他办法对本地的GGUF部署的DeepSeek模型进行训练呢?今天我们就反其道而行之…...
Flutter:动态表单(在不确定字段的情况下,生成动态表单)
关于数据模型:模型就是一种规范约束,便于维护管理,在不确定表单内会出现什么数据时,就没有模型一说。 这时就要用到动态表单(根据接口返回的字段,生成动态表单) 1、观察数据格式,定义…...
【Python项目】文本相似度计算系统
【Python项目】文本相似度计算系统 技术简介:采用Python技术、Django技术、MYSQL数据库等实现。 系统简介:本系统基于Django进行开发,包含前端和后端两个部分。前端基于Bootstrap框架进行开发,主要包括系统首页,文本分…...
C# ref 和 out 的使用详解
总目录 前言 在 C# 编程中,ref 和 out 是两个非常重要的关键字,它们都用于方法参数的传递,但用途和行为却有所不同。今天,我们就来深入探讨一下这两个关键字的用法和区别,让你在编程中能够得心应手地使用它们。 一、什…...
Ubuntu 24.04.1 LTS 本地部署 DeepSeek 私有化知识库
文章目录 前言工具介绍与作用工具的关联与协同工作必要性分析 1、DeepSeek 简介1.1、DeepSeek-R1 硬件要求 2、Linux 环境说明2.1、最小部署(Ollama DeepSeek)2.1.1、扩展(非必须) - Ollama 后台运行、开机自启: 2.2、…...
用 WOW.js 和 animate.css 实现动画效果
用 wow.js 就可以实现动画效果,但由于里面的动画样式太少,一般还会引入 animated.css 第一步:下载 选择合适的包管理器下载对应的内容 pnpm i wow.js animated.css --save 第二步:引入 在main.js中加入: import …...
1-知识图谱-概述和介绍
知识图谱:浙江大学教授 陈华军 知识图谱 1课时 http://openkg.cn/datasets-type/ 知识图谱的价值 知识图谱是有什么用? 语义搜索 问答系统 QA问答对知识图谱:结构化图 辅助推荐系统 大数据分析系统 自然语言理解 辅助视觉理解 例…...
论文解读:交大港大上海AI Lab开源论文 | 宇树机器人多姿态起立控制强化学习框架(二)
HoST框架核心实现方法详解 - 论文深度解读(第二部分) 《Learning Humanoid Standing-up Control across Diverse Postures》 系列文章: 论文深度解读 + 算法与代码分析(二) 作者机构: 上海AI Lab, 上海交通大学, 香港大学, 浙江大学, 香港中文大学 论文主题: 人形机器人…...
3.3.1_1 检错编码(奇偶校验码)
从这节课开始,我们会探讨数据链路层的差错控制功能,差错控制功能的主要目标是要发现并且解决一个帧内部的位错误,我们需要使用特殊的编码技术去发现帧内部的位错误,当我们发现位错误之后,通常来说有两种解决方案。第一…...
在rocky linux 9.5上在线安装 docker
前面是指南,后面是日志 sudo dnf config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo sudo dnf install docker-ce docker-ce-cli containerd.io -y docker version sudo systemctl start docker sudo systemctl status docker …...
Docker 运行 Kafka 带 SASL 认证教程
Docker 运行 Kafka 带 SASL 认证教程 Docker 运行 Kafka 带 SASL 认证教程一、说明二、环境准备三、编写 Docker Compose 和 jaas文件docker-compose.yml代码说明:server_jaas.conf 四、启动服务五、验证服务六、连接kafka服务七、总结 Docker 运行 Kafka 带 SASL 认…...
sqlserver 根据指定字符 解析拼接字符串
DECLARE LotNo NVARCHAR(50)A,B,C DECLARE xml XML ( SELECT <x> REPLACE(LotNo, ,, </x><x>) </x> ) DECLARE ErrorCode NVARCHAR(50) -- 提取 XML 中的值 SELECT value x.value(., VARCHAR(MAX))…...
Robots.txt 文件
什么是robots.txt? robots.txt 是一个位于网站根目录下的文本文件(如:https://example.com/robots.txt),它用于指导网络爬虫(如搜索引擎的蜘蛛程序)如何抓取该网站的内容。这个文件遵循 Robots…...
论文阅读:LLM4Drive: A Survey of Large Language Models for Autonomous Driving
地址:LLM4Drive: A Survey of Large Language Models for Autonomous Driving 摘要翻译 自动驾驶技术作为推动交通和城市出行变革的催化剂,正从基于规则的系统向数据驱动策略转变。传统的模块化系统受限于级联模块间的累积误差和缺乏灵活性的预设规则。…...
第一篇:Liunx环境下搭建PaddlePaddle 3.0基础环境(Liunx Centos8.5安装Python3.10+pip3.10)
第一篇:Liunx环境下搭建PaddlePaddle 3.0基础环境(Liunx Centos8.5安装Python3.10pip3.10) 一:前言二:安装编译依赖二:安装Python3.10三:安装PIP3.10四:安装Paddlepaddle基础框架4.1…...
命令行关闭Windows防火墙
命令行关闭Windows防火墙 引言一、防火墙:被低估的"智能安检员"二、优先尝试!90%问题无需关闭防火墙方案1:程序白名单(解决软件误拦截)方案2:开放特定端口(解决网游/开发端口不通)三、命令行极速关闭方案方法一:PowerShell(推荐Win10/11)方法二:CMD命令…...
React核心概念:State是什么?如何用useState管理组件自己的数据?
系列回顾: 在上一篇《React入门第一步》中,我们已经成功创建并运行了第一个React项目。我们学会了用Vite初始化项目,并修改了App.jsx组件,让页面显示出我们想要的文字。但是,那个页面是“死”的,它只是静态…...
