Mysql索引降维 优化查询 提高效率

本文涉及的产品
RDS MySQL Serverless 基础系列,0.5-2RCU 50GB
RDS MySQL Serverless 高可用系列,价值2615元额度,1个月
云数据库 RDS MySQL,高可用系列 2核4GB
简介: Mysql索引降维 优化查询 提高效率

写在前面

在前一篇文章中,我们已经介绍了索引、索引的优化规则等等

原文链接:Siam博客 mysql索引优化

在其中我们有引申出组合索引,多个单字段索引冲突两个知识点。

本文章主要是与后者有关联。

在原文中,我们使用了下面的例子

现在有这样子的数据量:
100W条数据 user_name=’我是用户名’
100条数据 user_phone=’110′
5条数据 user\_name=’我是用户名’ and user\_phone=’110′
假设有这样子一条语句:
select * from test where user\_name = '我是用户名' and user\_phone='110'
有两个字段都有索引可用,mysql会选择一个使用。这是属于mysql的内部处理判断
正常情况下,如果用user_phone索引生效的话,会很快得到结果(先筛选出100条 再筛选)
如果user\_name生效,则要先筛选100W条数据,再筛选user\_phone
mysql内部的错误判断可能使得user_name索引生效,此时效率就会很低了,我们可以强制使用某个索引

指定使用索引的意义

从以上例子中,我们可以思考并归纳。能提升效率的核心是:在一开始就尽可能地筛选出准确的数据

所以当我们发现mysql可能处理出错的情况时,可以手动指定使用更优的索引来提高查询效率。

这个可以称为索引降维

降维

数据的选择度越大,则维度越大。

降维,按我个人的理解是:在大量的数据中,一层一层地筛选过滤,维度也会逐渐减低。

点线面中,共有黑红两种颜色。

目标:筛选出所有红色的点

步骤:选出所有带有红色点的面 –> 选出所有带有红色点的线 –> 在线上选出所有红色点

索引降维

在老旧的mysql版本中,where的条件顺序还会很大影响执行结果。

比如在上面的举例中,用条件语句来举例,而不是索引

select * from test where user\_name = '我是用户名' and user\_phone='110'

select * from test where user_phone='110' and user_name = '我是用户名'

这两个语句会出现上面索引冲突时 mysql没有使用更优索引的情况一样,第一条语句会先筛选出100W条数据,再筛选user_phone=110
> 然而在后续的mysql发展中,sql构造器优化器会自动帮我们排序执行,这种问题已不太需要人工去调整。
但是当我们建立组合索引的时候,则会根据我们的选择顺序来构建了。
比如有这么一个索引

index user_info (user_name, user_phone)

我们可以用大小分类的情况举例看一下

└名字一 └──user_phone 110 └──user_phone 120 └──user_phone 119 └名字二 └──user_phone 110 └──user_phone 120 └──user_phone 119 └名字三 └──user_phone 110 └──user_phone 120 └──user_phone 119

而如果我们把顺序调整成`(user_phone, user_name)`
那么就可以把组合索引看成

└─110 └──user_name 名字一 └──user_name 名字二 └──user_name 名字三 └─120 └──user_name 名字一 └──user_name 名字二 └──user_name 名字三 └─119 └──user_name 名字一 └──user_name 名字二 └──user_name 名字三

两种情况,都会在某些场景下有自己的优势,所以我们就需要`结合自己的业务数据`来进行选择啦。
用我们的老例子来说:  
以名字来区分,第一次筛选出现100W条数据,然后再筛选手机号。  
以手机号来区分,第一次筛选出现100条数据,然后再筛选用户名。
同样的情况还出现在`分表`中,用什么条件来分表也是极其重要的。
分表中,如果我们以订单的年份作为分表条件,想要搜索ID=3的会员在2019年某个月份日期的订单,那么我们需要先搜索2019年的表(一年的订单假设有100W条记录),然后再筛选用户ID和其他月份等条件。
如果我们以订单的年份+月份作为分表条件(只是举例,有很多分表条件可以决定),那么初步筛选的数据就会少了很多了,后续的筛选步骤也会更快完成。
总结
==
在分表、组合索引等等场景下,我们可以结合业务数据,进行降维的顺序思考,尽可能地`在一开始就筛选出比较准确的数据`,在后续的筛选中则只需要遍历检查很少的一部分数据,已达到提高查询效率的效果。
本文由Siam博客原创,原文地址:[原文地址](https://www.siammm.cn/archives/103)
相关实践学习
每个IT人都想学的“Web应用上云经典架构”实战
本实验从Web应用上云这个最基本的、最普遍的需求出发,帮助IT从业者们通过“阿里云Web应用上云解决方案”,了解一个企业级Web应用上云的常见架构,了解如何构建一个高可用、可扩展的企业级应用架构。
MySQL数据库入门学习
本课程通过最流行的开源数据库MySQL带你了解数据库的世界。   相关的阿里云产品:云数据库RDS MySQL 版 阿里云关系型数据库RDS(Relational Database Service)是一种稳定可靠、可弹性伸缩的在线数据库服务,提供容灾、备份、恢复、迁移等方面的全套解决方案,彻底解决数据库运维的烦恼。 了解产品详情: https://www.aliyun.com/product/rds/mysql 
目录
相关文章
|
SQL 存储 大数据
某互联网大厂亿级大数据服务平台的建设和实践
某互联网大厂亿级大数据服务平台的建设和实践
755 0
|
存储 物联网 Shell
振南技术干货集:深入浅出的Bootloader(4)
振南技术干货集:深入浅出的Bootloader(4)
|
9月前
|
物联网 测试技术 API
时序数据库 InfluxDB 3.0 版本性能实测报告:写入吞吐量提升效果验证
TSBS 测试表明,对于少于 100 万台设备的数据集,InfluxDB OSS 3.0 的数据写入速度实际上比 InfluxDB OSS 1.8 更慢。 对于 100 万台及以上设备的数据集,InfluxDB OSS 3.0 的数据写入性能才开始超过 InfluxDB OSS 1.8。 InfluxDB OSS 3.0 的数据写入接口与 InfluxDB 1.8 并不兼容,用户无法顺利迁移。
735 7
|
存储 缓存 安全
Java性能优化(二):Java基础-String对象及其性能优化
在深入探讨了String字符串的性能优化后,我们认识到优化字符串处理对提升系统整体性能的重要性。Java在版本迭代中,通过精心调整成员变量和内存管理机制,不断对String对象进行优化,以更高效地使用内存资源。String对象的不可变性是Java语言设计中的一个关键特性,它不仅确保了字符串的安全性,也为字符串常量池的实现提供了基础。通过减少相同值的字符串对象的重复创建,常量池有效地节约了内存空间。然而,不可变性也带来了挑战。在处理长字符串拼接时,我们需要显式使用类来避免性能下降。
287 1
|
SQL 分布式计算 资源调度
MaxCompute操作报错合集之执行SQL Union All操作时,数据类型产生报错,该怎么解决
MaxCompute是阿里云提供的大规模离线数据处理服务,用于大数据分析、挖掘和报表生成等场景。在使用MaxCompute进行数据处理时,可能会遇到各种操作报错。以下是一些常见的MaxCompute操作报错及其可能的原因与解决措施的合集。
341 1
|
机器学习/深度学习 数据采集 人工智能
数据工作中的自动化与AI融合实践
【8月更文第13天】随着大数据和人工智能(AI)技术的发展,数据处理和分析变得越来越重要。本文将探讨如何通过自动化工具和AI技术来优化数据处理流程,包括数据清洗、特征工程、模型训练以及结果可视化等步骤。我们将使用Python编程语言及其相关库(如Pandas、Scikit-learn和TensorFlow)作为实现手段。
901 0
|
关系型数据库 MySQL
清理MySQL的binlog日志
清理MySQL的binlog日志
1552 0
|
JavaScript
cnpm 的安装与使用
本文介绍了npm和cnpm的概念、安装nodejs的步骤,以及cnpm的安装和使用方法,提供了通过配置npm使用中国镜像源来加速包下载的替代方案,并说明了如何恢复npm默认仓库地址。
cnpm 的安装与使用
|
SQL 时序数据库
influxdb 进行数据删除和修改
influxdb 进行数据删除和修改
2799 5
|
前端开发
async/await返回的promise被解析为undefined的可能原因
`async/await` 通常与 `Promise` 一起使用,但如果返回的 `Promise` 被解析为 `undefined`,可能有几个原因。以下是一些可能的情况和解决方法