索引与慢查询优化
知识回顾: 数据都是存在硬盘上的, 那查询数据不可避免的需要进行 IO 操作
索引在 MySQL 中也叫做 "键", 是存储引擎用于快速找到记录的一种数据结构.
- primary key
- unique key
- index key
注意 foreign key 不是用来加速查询用的, 不在我们研究范围之内, 上面三种 key 前两种除了有加速查询的效果之外还有额外的约束条件 (primary key: 非空且唯一, unique key: 唯一), 而 index key 没有任何约束功能只会帮你加速查询
索引就是一种数据结构, 类似于书的目录. 意味着以后再查数据应该先找目录再找数据, 而不是用翻页的方式查询数据
本质都是: 通过不断地缩小想要获取数据的范围来筛选出最终想要的结果, 同时把随机的事件变成顺序的事件, 也就是说, 有了这种索引机制, 我们可以总是用同一种查找方式来锁定数据.
索引的影响:
在表中有大量数据的前提下, 创建索引速度会很慢
在索引创建完毕后, 对表的查询性能会大幅度提升, 但是写的性能会降低
b + 树
https://images2017.cnblogs.com/blog/1036857/201709/1036857-20170912011123500-158121126.png
b + 树通过一层一层进行区域范围划分逐步缩小查询范围来提高查询速度的
只有叶子结点存放真实数据, 根和树枝节点存的仅仅是虚拟数据
查询次数由树的层级决定, 层级越低次数越少
一个磁盘块儿的大小是一定的, 那也就意味着能存的数据量是一定的. 如何保证树的层级最低呢? 一个磁盘块儿存放占用空间比较小的数据项
思考我们应该给我们一张表里面的什么字段字段建立索引能够降低树的层级高度 >>> 主键 id 字段
聚集索引 (primary key)
聚集索引其实指的就是表的主键, innodb 引擎规定一张表中必须要有主键. 先来回顾一下存储引擎.
myisam 在建表的时候对应到硬盘有几个文件 (三个)?
innodb 在建表的时候对应到硬盘有几个文件 (两个)?frm 文件只存放表结构, 不可能放索引, 也就意味着 innodb 的索引跟数据都放在 idb 表数据文件中.
特点: 叶子结点放的一条条完整的记录
辅助索引 (unique,index)
辅助索引: 查询数据的时候不可能都是用 id 作为筛选条件, 也可能会用 name,password 等字段信息, 那么这个时候就无法利用到聚集索引的加速查询效果. 就需要给其他字段建立索引, 这些索引就叫辅助索引
特点: 叶子结点存放的是辅助索引字段对应的那条记录的主键的值 (比如: 按照 name 字段创建索引, 那么叶子节点存放的是:{name 对应的值: name 所在的那条记录的主键值})
select name from user where name='jason';
上述语句叫覆盖索引: 只在辅助索引的叶子节点中就已经找到了所有我们想要的数据
select age from user where name='jason';
上述语句叫非覆盖索引, 虽然查询的时候命中了索引字段 name, 但是要查的是 age 字段, 所以还需要利用主键才去查找
来源: http://www.bubuko.com/infodetail-3063161.html