手把手教你给 SQL 做个优化(二)

本文涉及的产品
RDS MySQL Serverless 基础系列,0.5-2RCU 50GB
云数据库 RDS MySQL,集群系列 2核4GB
推荐场景:
搭建个人博客
RDS MySQL Serverless 高可用系列,价值2615元额度,1个月
简介: 在开始之前,咱们要知道:如果我的 SQL 语句执行的足够快,还有没有必要去做优化? 完全没有必要对吧 所以我们一般说,要给 SQL 做个优化,那肯定就是这条 SQL 语句执行的比较慢了

通过 EXPLAIN 分析 SQL 是怎样执行的

只要说 SQL 调优,那就离不开 EXPLAIN

EXPLAIN SELECT * FROMtableWHERE id < 100 ORDER BY a;

29.jpg

咱们能够看到有好几个参数:

  • id :每个执行计划都会有一个 id ,如果是一个联合查询的话,这里就会显示好多个 id
  • select_type :表示的是 select 查询类型,常见的就是 SIMPLE (普通查询,也就是没有联合查询/子查询), PRIMARY (主查询), UNION ( UNION 中后面的查询), SUBQUERY (子查询)
  • table :执行查询计划的表,在这里我查的就是 table ,所以显示的是 table, 那如果我给 table 起了别名 a ,在这里显示的就是 a
  • type :查询所执行的方式,这是咱们在分析 SQL 优化的时候一个非常重要的指标,这个值从好到坏依次是: system > const > eq_ref > ref > range > index > ALL
  • system/const :说明表中只有一行数据匹配,这个时候根据索引查询一次就能找到对应的数据
  • eq_ref :使用唯一索引扫描,这个经常在多表连接里面,使用主键和唯一索引作为关联条件时可以看到
  • ref :非唯一索引扫描,也可以在唯一索引最左原则匹配扫描看到
  • range :索引范围扫描,比如查询条件使用到了 < , > , between 等条件
  • index :索引全表扫描,这个时候会遍历整个索引树
  • ALL :表示全表扫描,也就是需要遍历整张表才能找到对应的行
  • possible_keys :表示可能使用到的索引
  • key :实际使用到的索引
  • key_len :使用的索引长度
  • ref :关联 id 等信息
  • rows :找到符合条件时,所扫描的行数,在这里虽然有 10 万条数据,但是因为索引的缘故,所以扫描了 99 行的数据
  • Extra :额外的信息,常见的有以下几种
  • Using where :不用读取表里面的所有信息,只需要通过索引就可以拿到需要的数据,这个过程发生在对表的全部请求列都是同一个索引部分时
  • Using temporary :表示 mysql 需要使用临时表来存储结果集,常见于 group by / order by
  • Using filesort :当查询的语句中包含 order by 操作的时候,而且 order by 后面的内容不是索引,这样就没有办法利用索引完成排序,就会使用"文件排序",就像例子中给出的,建立的索引是 id , 但是我的查询语句 order by 后面是 a ,没有办法使用索引
  • Using join buffer :使用了连接缓存
  • Using index :使用了覆盖索引

如果对这些参数了解的非常不错,那么 EXPLAIN 这块内容就难不住你了

Show Profile 分析下 SQL 执行性能

通过 EXPLAIN 分析执行计划,只能说明 SQL 的外部执行情况,如果想要知道 mysql 具体是如何查询的,需要通过 Show Profile 来分析

可以通过 SHOW PROFILES; 语句来查询最近发送给服务器的 SQL 语句,默认情况下是记录最近已经执行的 15 条记录,如下图我们可以看到:

30.jpg

我想看具体的一条语句,看到 Query_ID 了嘛?然后运行下 SHOW PROFILE FOR QUERY 82; 这条命令就可以了:

31.jpg

可以看到,在结果中, Sending data 耗时是最长的,这是因为此时 mysql 线程开始读取数据并且把这些数据返回到客户端,在这个过程中会有大量磁盘 I/O 操作

通过这样的分析,我们就能知道, SQL 语句在查询过程中,到底是 磁盘 I/O 影响了查询速度,还是 System lock 影响了查询速度,知道了病症所在,接下来对症下药就容易多了

分页查询怎么可以更快一些

在使用分页查询时,都会使用 limit 关键字

但是对于分页查询,其实还可以优化一步

我这里给出的数据库不是太好,因为它太简单了,看不出来有什么区别,我使用目前项目上正在用的表来做个实验,可以看下区别(使用的 SQL 语句如下面):

EXPLAIN SELECT * FROM `te_paper_record` ORDER BY id LIMIT 10000, 20;
EXPLAIN SELECT * FROM `te_paper_record` WHERE id >= ( SELECT id FROM `te_paper_record` ORDER BY id LIMIT 10000, 1) LIMIT 20;

32.jpg

33.jpg

上面一张图片,我没有使用子查询,可以看到执行了 0.033s ,下面的查询语句,我使用了子查询去做优化,能够看到执行了 0.007s ,优化的结果还是很显而易见的

那么,为什么使用了子查询,查询的速度就提上来了呢,这是因为当我们没有使用子查询时,查询到的 10020 行数据都返回回来了,接下来要对这 10020 行数据再进行过滤操作

那可不可以直接就返回需要的 20 行数据呢,这样就不需要再做过滤操作了,直接返回就可以了嘛

你也太聪明了吧。子查询就是在做这件事情

所以查询时间上有了一个很大的优化

正确的 select 打开方式

在查询时,有时为了省事,直接使用 select * from table where id = 1 这样的 SQL 语句,但是这样的写法在一些环境下是会存在一定的性能损耗的

所以最好的 select 查询就是,需要什么字段就查询什么字段

一般在查询时,都会有条件,按照条件查找

这个时候正确的 select 打开方式是什么呢?

如果可以通过主键索引的话, where 后面的条件,优先选择主键索引

为什么呢?这就要知道 MySQL 的存储规则

MySQL 常用的存储引擎有 MyISAM 和 InnoDB , InnoDB 会创建主键索引,而主键索引属于聚簇索引,也就是在存储数据时,索引是基于 B+ 树构成的,具体的行数据则存储在叶子节点

也就是说,如果是通过主键索引查询的,会直接搜索 B+ 树,从而查询到数据

如果不是通过主键索引查询的,需要先搜索索引树,得到在 B+ 树上的值,再到 B+ 树上搜索符合条件的数据,这个过程就是“回表”

很显然,回表能够产生时间。

这也是为什么建议, where 后面的条件,优先选择主键索引

其他调优

看完上面的,心里应该就大概有数了, SQL 调优主要就是建立索引/防止产生锁等待/使用恰当的 SQL 语句去查询

但是,如果问你除了索引,除了上面这些手段,还有没有其他调优方式

啥?竟然还有?!

有的,这就需要跳出来,不要局限在具体的 SQL 语句上了,需要在数据库设计之初就考虑好

比如说,我们常说的要遵循三范式,但是在有的业务场景里面,如果在数据库里面多几个冗余字段的话,可能要比严格遵循三范式带来的性能要好很多。

但是这点就及其考验平时的积累了,阿粉在这里把这一点提出来之后,希望读者们可以看看自己项目上目前用的数据库有没有多余的字段,为什么要这样设计呢?这样多去观察,你的技术能力想不提高都很难

以上,就这样啦~

相关实践学习
如何快速连接云数据库RDS MySQL
本场景介绍如何通过阿里云数据管理服务DMS快速连接云数据库RDS MySQL,然后进行数据表的CRUD操作。
全面了解阿里云能为你做什么
阿里云在全球各地部署高效节能的绿色数据中心,利用清洁计算为万物互联的新世界提供源源不断的能源动力,目前开服的区域包括中国(华北、华东、华南、香港)、新加坡、美国(美东、美西)、欧洲、中东、澳大利亚、日本。目前阿里云的产品涵盖弹性计算、数据库、存储与CDN、分析与搜索、云通信、网络、管理与监控、应用服务、互联网中间件、移动服务、视频服务等。通过本课程,来了解阿里云能够为你的业务带来哪些帮助 &nbsp; &nbsp; 相关的阿里云产品:云服务器ECS 云服务器 ECS(Elastic Compute Service)是一种弹性可伸缩的计算服务,助您降低 IT 成本,提升运维效率,使您更专注于核心业务创新。产品详情: https://www.aliyun.com/product/ecs
相关文章
|
20天前
|
SQL Oracle 数据库
使用访问指导(SQL Access Advisor)优化数据库业务负载
本文介绍了Oracle的SQL访问指导(SQL Access Advisor)的应用场景及其使用方法。访问指导通过分析给定的工作负载,提供索引、物化视图和分区等方面的优化建议,帮助DBA提升数据库性能。具体步骤包括创建访问指导任务、创建工作负载、连接工作负载至访问指导、设置任务参数、运行访问指导、查看和应用优化建议。访问指导不仅针对单条SQL语句,还能综合考虑多条SQL语句的优化效果,为DBA提供全面的决策支持。
55 11
|
2月前
|
SQL 缓存 监控
大厂面试高频:4 大性能优化策略(数据库、SQL、JVM等)
本文详细解析了数据库、缓存、异步处理和Web性能优化四大策略,系统性能优化必知必备,大厂面试高频。关注【mikechen的互联网架构】,10年+BAT架构经验倾囊相授。
大厂面试高频:4 大性能优化策略(数据库、SQL、JVM等)
|
2月前
|
SQL 缓存 数据库
SQL慢查询优化策略
在数据库管理和应用开发中,SQL查询的性能优化至关重要。慢查询优化不仅可以提高应用的响应速度,还能降低服务器负载,提升用户体验。本文将详细介绍针对SQL慢查询的优化策略。
|
2月前
|
SQL 存储 BI
gbase 8a 数据库 SQL合并类优化——不同数据统计周期合并为一条SQL语句
gbase 8a 数据库 SQL合并类优化——不同数据统计周期合并为一条SQL语句
|
2月前
|
SQL 数据库
gbase 8a 数据库 SQL优化案例-关联顺序优化
gbase 8a 数据库 SQL优化案例-关联顺序优化
|
2月前
|
SQL 数据库 UED
SQL性能提升秘籍:5步优化法与10个实战案例
在数据库管理和应用开发中,SQL查询的性能优化至关重要。高效的SQL查询不仅可以提高应用的响应速度,还能降低服务器负载,提升用户体验。本文将分享SQL优化的五大步骤和十个实战案例,帮助构建高效、稳定的数据库应用。
94 3
|
2月前
|
SQL 存储 缓存
如何优化SQL查询性能?
【10月更文挑战第28天】如何优化SQL查询性能?
184 10
|
2月前
|
SQL 存储 缓存
SQL Server 数据太多如何优化
11种优化方案供你参考,优化 SQL Server 数据库性能得从多个方面着手,包括硬件配置、数据库结构、查询优化、索引管理、分区分表、并行处理等。通过合理的索引、查询优化、数据分区等技术,可以在数据量增大时保持较好的性能。同时,定期进行数据库维护和清理,保证数据库高效运行。
|
3月前
|
SQL 资源调度 分布式计算
如何让SQL跑快一点?(优化指南)
这篇文章主要探讨了如何在阿里云MaxCompute(原ODPS)平台上对SQL任务进行优化,特别是针对大数据处理和分析场景下的性能优化。
|
2月前
|
SQL 缓存 监控
SQL性能提升指南:五大优化策略与十个实战案例
在数据库性能优化的世界里,SQL优化是提升查询效率的关键。一个高效的SQL查询可以显著减少数据库的负载,提高应用响应速度,甚至影响整个系统的稳定性和扩展性。本文将介绍SQL优化的五大步骤,并结合十个实战案例,为你提供一份详尽的性能提升指南。
63 0