MySQL查询优化

本文涉及的产品
云数据库 RDS MySQL Serverless,0.5-2RCU 50GB
云数据库 RDS MySQL Serverless,价值2615元额度,1个月
简介: 总的来说,主要是针对MySQL本身的查询流程和引擎实现来做优化。但实际我们开发程序的时候,在应用层可以做缓存来优化性能,这样可以大大减少MySQL的请求和查询次数。另一方面,MySQL的索引非常重要,理解索引的原理,创建合适的索引可以极大地提升查询的性能。使用索引的主要好处就是可以在查询的时候扫描更少的行。

为什么查询会慢?


查询慢的原因可能很多,比如网络原因、锁争用等等。但最基本的原因可能是访问的数据太多。要么可能访问了太多的行,要么可能访问了太多的列,要么可能MySQL在查询的时候需要分析大量超过需要的行。


查询优化

一个查询根据不同的场景,一般可以通过下面的方式来进行优化:

使用COUNT *

在使用COUNT统计行数时,COUNT(*)是性能最高的。


使用LIMIT

有时候查询并不需要返回所有的结果集,这时候可以加LIMIT限制返回多少。这在分页的场景下很常见。

MySQL在进行UNION操作的时候,如果把LIMIT写在外查询里,会先将两个子查询的所有数据放在临时表,然后取前xx行。这样性能其实是比较低的,更推荐的做法是把LIMIT同时也到子查询里。

有时候可以使用LIMIT 1来代替MINMAX函数。因为这两个函数需要全表扫描。


不要查询所有列

有时候为了方便,会直接写SELECT *来查询所有列的数据。但可能使用的时候不一定要使用到所有列。这个时候可以只查询部分需要用到的列。

但有时候可能也有例外,因为这样做确实可以简化开发,而且有时候应用程序里面可能会有缓存机制,这样多个查询可能可以复用这个缓存。


经常查询的列建立索引

在前面的文章《MySQL索引原理》及《MySQL索引使用策略和优化》中,我们介绍了MySQL的索引。在经常查询的列上面建立索引,可以让MySQL尽可能地扫描少的行。

但这里也需要注意,维护索引是有代价的,所以需要自己去权衡时候使用索引。还有一点就是MySQL的索引是基于“最左匹配”原则的。详情可以参考之前的文章。


分解复杂查询

有时候一个复杂查询可能会“很大”,需要扫描许多行,关联很多表。这个时候可以把它分解成很多个小的查询。这样做有很多好处:

  • 让缓存的效率更高
  • 执行单个查询可以减少锁的竞争
  • 更容易对数据库进行拆分
  • 减少冗余记录的查询:有时候关联查询可能会重复查询同样的数据行。

当然,分解后也会带来弊端,就是发生的查询数量多了,MySQL的连接数就多了,可能会带来网络上的一些开销。但MySQL一般是放在内网的,网络一般会很快,所以不会有太大的影响。


反范式设计数据表

在设计数据表的时候,为了性能上的优化,可以反范式地设计表。这样可以减小表的关联,加快查询的速度。


使用IN

MySQL在查询的时候使用IN()时,会先将IN列表中的数据进行排序,然后通过二分查找的方式来确定列表中的值时候满足条件,这是一个O(log n)复杂度的操作,而如果是OR的话,复杂度是O(n),所以如果对IN列表中有大量取值的时候,使用IN会更快一些。

但尽量不要使用IN加子查询。因为MySQL会将相关的外层表压到子查询中,效率很低。如果是需要用到IN加子查询的时候,建议使用EXISTS()等效查询来做。


不使用OFFSET

OFFSET在分页的时候很常见。一旦页码过大,OFFSET和导致MySQL扫描大量不需要的行然后丢掉。那如何解决这个问题呢?有两种方式。

第一种方式是从前端就限制了用户不能直接访问太大的页码。比如百度搜索结果下面的分页,限制了用户很难访问到很大的页码。

第二种方式是使用主键来辅助。比如上一页返回的id的1000,那下一页就可以直接WHERE查找id大于1000且小于1020。这样查的时候就可以不用OFFSET了,MySQL也只需要扫描很少的行。但这样有一个弊端,就是有些数据可能被删掉了,那每页的范围和数量就不太好控制。


总结


总的来说,主要是针对MySQL本身的查询流程和引擎实现来做优化。但实际我们开发程序的时候,在应用层可以做缓存来优化性能,这样可以大大减少MySQL的请求和查询次数。

另一方面,MySQL的索引非常重要,理解索引的原理,创建合适的索引可以极大地提升查询的性能。使用索引的主要好处就是可以在查询的时候扫描更少的行。

相关实践学习
基于CentOS快速搭建LAMP环境
本教程介绍如何搭建LAMP环境,其中LAMP分别代表Linux、Apache、MySQL和PHP。
全面了解阿里云能为你做什么
阿里云在全球各地部署高效节能的绿色数据中心,利用清洁计算为万物互联的新世界提供源源不断的能源动力,目前开服的区域包括中国(华北、华东、华南、香港)、新加坡、美国(美东、美西)、欧洲、中东、澳大利亚、日本。目前阿里云的产品涵盖弹性计算、数据库、存储与CDN、分析与搜索、云通信、网络、管理与监控、应用服务、互联网中间件、移动服务、视频服务等。通过本课程,来了解阿里云能够为你的业务带来哪些帮助     相关的阿里云产品:云服务器ECS 云服务器 ECS(Elastic Compute Service)是一种弹性可伸缩的计算服务,助您降低 IT 成本,提升运维效率,使您更专注于核心业务创新。产品详情: https://www.aliyun.com/product/ecs
目录
相关文章
|
2月前
|
关系型数据库 MySQL 数据库
MySQL索引和查询优化
MySQL索引和查询优化
35 1
|
3月前
|
SQL 缓存 关系型数据库
MySQL技能完整学习列表6、查询优化——3、查询缓存——4、SQL优化技巧
MySQL技能完整学习列表6、查询优化——3、查询缓存——4、SQL优化技巧
65 0
|
3月前
|
存储 SQL 关系型数据库
三高Mysql - Mysql索引和查询优化讲解(偏理论部分)
三高Mysql - Mysql索引和查询优化讲解(偏理论部分)
53 0
|
9月前
|
存储 算法 关系型数据库
第10章 索引优化与查询优化【2.索引及调优篇】【MySQL高级】3
第10章 索引优化与查询优化【2.索引及调优篇】【MySQL高级】3
128 0
|
5月前
|
SQL 缓存 关系型数据库
MySQL调优之关联查询、子查询优化
MySQL调优之关联查询、子查询优化
356 0
|
1月前
|
缓存 关系型数据库 MySQL
MySQL查询优化:提速查询效率的13大秘籍(合理使用索引合并、优化配置参数、使用分区优化性能、避免不必要的排序和group by操作)(下)
MySQL查询优化:提速查询效率的13大秘籍(合理使用索引合并、优化配置参数、使用分区优化性能、避免不必要的排序和group by操作)(下)
|
1月前
|
缓存 关系型数据库 MySQL
MySQL 查询优化:提速查询效率的13大秘籍(索引设计、查询优化、缓存策略、子查询优化以及定期表分析和优化)(中)
MySQL 查询优化:提速查询效率的13大秘籍(索引设计、查询优化、缓存策略、子查询优化以及定期表分析和优化)(中)
|
15天前
|
缓存 关系型数据库 MySQL
【专栏】提升MySQL性能和高可用性的策略,包括索引优化、查询优化和事务管理
【4月更文挑战第27天】本文探讨了提升MySQL性能和高可用性的策略,包括索引优化、查询优化和事务管理。通过合理使用B-Tree和哈希索引,避免过度索引,以及优化查询语句和利用查询缓存,可以改善性能。事务管理中,应减小事务大小并及时提交,以保持系统效率。主从或双主复制可增强高可用性。综合运用这些方法,并根据实际需求调整,是优化MySQL的关键。
|
1月前
|
存储 关系型数据库 MySQL
MySQL 查询优化:提速查询效率的13大秘籍(避免使用SELECT *、分页查询的优化、合理使用连接、子查询的优化)(上)
MySQL 查询优化:提速查询效率的13大秘籍(避免使用SELECT *、分页查询的优化、合理使用连接、子查询的优化)(上)
|
3月前
|
存储 关系型数据库 MySQL
MySQL技能完整学习列表6、查询优化——1、EXPLAIN命令的使用——2、索引优化
MySQL技能完整学习列表6、查询优化——1、EXPLAIN命令的使用——2、索引优化
24 0