- 按楼梯从低到高,无出现跳跃的情况--此时符合最左前缀原则,索引不会失效
文章插图
- 出现跳跃的情况
- 直接第一层name都不走,当然都失效
文章插图
- 走了第一层,但是后续直接第三层,只有出现跳跃情况前的不会失效(此处就只有name成功)
文章插图
- 同时 , 这个顺序并不是由我们where中的排列顺序决定,比如:
- where name='小米科技' and status='1' and address='北京市'
- where status='1' and name='小米科技' and address='北京市'
其实是因为我们MySQL有一个Optimizer(查询优化器),查询优化器会将SQL进行优化,选择最优的查询计划来执行 。
- 关于这个查询优化器,后续文章我们也会谈谈MySQL的逻辑架构与存储引擎
- 查询频次高,且数据量多的表
- 最好从where子句的条件中提取 , 如果where子句中的组合比较多,那么应当挑选最常用、过滤效果最好的列的组合 。
- 最好用唯一索引,区分度越高,使用索引的效率越高
- 不是越多越好,维护也需要时间和空间代价,建议单张表索引不超过 5 个
因为 MySQL 优化器在选择如何优化查询时,会根据统一信息,对每一个可以用到的索引来进行评估 , 以生成出一个最好的执行计划,如果同时有很多个索引都可以用于查询,就会增加 MySQL 优化器生成执行计划的时间,同样会降低查询性能 。比如:
我们创建了三个单列索引,name , status,address当我们where中根据status和address两个字段来查询时,数据库只会选择最优的一个索引,不会所有单列索引都使用 。最优的索引:具体是指所查询表中 , 辨识度最高(所占比例最少)的索引列,比如此处address中有一个辨识度很高的 '西安市'数据;
文章插图
?
- 使用短索引,索引创建之后也是使用硬盘来存储的 , 因此提升索引访问的I/O效率,也可以提升总体的访问效率 。假如构成索引的字段总长度比较短,那么在给定大小的存储块内可以存储更多的索引值,相应的可以有效的提升MySQL访问索引的I/O效率 。
- 利用最左前缀 , 比如有N个字段,我们不一定需要创建N个索引,可以用复合索引
也就是说 , 我们尽量创建复合索引,而不是单列索引
创建复合索引: CREATE INDEX idx_name_email_status ON tb_seller(name,email,status);就相当于 对name 创建索引 ; 对name , email 创建了索引 ; 对name , email, status 创建了索引 ;
举个栗子假设我们有这么一个表,id为主键,没有创建索引:CREATE TABLE `tuser` (`id` int(11) NOT NULL,`name` varchar(32) DEFAULT NULL,`age` int(11) DEFAULT NULL,PRIMARY KEY (`id`),) ENGINE=InnoDB
如果要在此处建立复合索引,我们要遵循什么原则呢??通过调整顺序,可以少维护一个索引
- 比如我们的业务需求里边 , 有如下两种查询方式:
- 根据name查询
- 根据name和age查询
而如果我们通过调整顺序,改成(name,age),就能实现我们的需求了,无需再维护一个name索引 , 这就是通过调整顺序,可以少维护一个索引 。
考虑空间->短索引
- 比如我们的业务需求里边,有以下两种查询方式:
- 根据name查询
- 根据age查询
- 根据name和age查询
- 建立联合索引(name,age),建立单列索引:age索引 。
- 建立联合索引(age,name),建立单列索引:name索引 。
这两种方案都能实现我们的需求 , 这个时候我们就要考虑空间了,name字段是比age字段大的 , 显然方案1所耗费的空间是更小的,所以我们更倾向于方案1 。
推荐阅读
- 我的世界怎么用附魔台附魔书(我的世界用高级附魔台怎么附魔)
- MySQL 索引失效-模糊查询,最左匹配原则,OR条件等。
- 30 《吐血整理》高级系列教程-吃透Fiddler抓包教程-Fiddler如何抓取Android7.0以上的Https包-番外篇
- MySQL 全局锁、表级锁、行级锁,你搞清楚了吗?
- llinux下mysql建库、新建用户、用户授权、修改用户密码
- RedHat7.6安装mysql8步骤
- 29 《吐血整理》高级系列教程-吃透Fiddler抓包教程-Fiddler如何抓取Android7.0以上的Https包-终篇
- 究极无敌细节版 Mysql索引
- Mysql通过Canal同步Elasticsearch
- MySQL的日志文件