索引的引入

MySQL官方定义:帮助MySQL高效获取数据的数据结构
优点:
缺点:
新建一个表:
mysql> CREATE TABLE index_demo(
-> c1 INT,
-> c2 INT,
-> c3 CHAR(1),
-> PRIMARY KEY(c1)
-> ) ROW_FORMAT = Compact;
建立目录:快速定位记录所在的页
下一个数据页中用户记录的主键值必须大于上一个页中用户记录的主键值
给所有的页建立一个目录项
将几个目录项在物理存储器上连续存储(比如:数组),就可以实现根据主键值快速查找某条记录的功能了
比如查找主键值为20的记录,查找过程分两步:
至此,针对数据页的简易目录就搞定了,这个目录的别名就称为索引
迭代一次;目录项记录的页

专门新分配了页10来存储目录项记录。目录项记录和普通的用户记录不同点如下:
相同点:两者使用一样的数据页,都会主键值生成Page Directory(页目录),从而在按照主键值进行查找时可以使用二分法来加快查询速度
迭代两次:多个目录项记录的页

当我们插入一条主键值为320的用户记录之后需要两个新的数据页
迭代三次:目录项记录页的目录页

生成一个存储更高级目录项的 页33,如果用户记录的主键值在[1,320)之间,则到页30中查找更详细的目录项记录,如果主键值不小于320的话,就到页32中查找更详细的目录项记录
B+树
上述结构可以用B+树这个数据结构描述

一个B+树节点其实可以分为好多层,规定最底层存储用户记录,其余都是目录项记录页
索引按照物理实现方式可分为2种:聚簇(聚集)、非聚簇(非聚集)索引。有时也把非聚簇索引称为二级索引或者辅助索引
特点:
1、使用记录主键值的大小进行记录和页的排序,这包括三方面含义
-页内的记录按照主键的大小顺序排成一个单项链表
-各个存放用户记录的页也是根据页中用户记录的主键大小顺序排成一个双向链表
-存放目录项记录的页分为不同层次,在同一层次中的页根据目录项几轮的主键大小顺序排成一个双向链表
2、B+树的叶子节点存储完整的用户记录(完整的用户记录指存储了所有列的指,包括隐藏列)
优点:
-数据访问更快,聚簇索引将索引将数据保存在同一个B+树中,因此从聚簇索引中获取的数据比非聚簇索引更快
-聚簇索引对于主键的排序查找、范围查找速度非常快
-按照聚簇排列顺序,查询显示一定范围数据时,由于数据紧密相连,数据库不用从多个数据块中提取数据,节省大量IO操作
缺点:
-插入速度严重依赖于插入顺序,按照逐渐的顺序插入式最快的方式,否则将会出现页分类,严重影响性能。对于InnoDB表,一般会定义一个自增的ID列为主键
-更新主键的代价很高,因为将会导致被更新的行移动。对于InnoDB表,一般定义主键为不可更新
-二级索引访问需要二次索引查找,第一次找到主键值,第二次根据主键值找到行数据

回表:如果某个查询语句使用了二级索引,但是查询的数据不是主键值,这时在二级索引找到主键值后,需要去聚簇索引中获得数据行,这个过程就叫作「回表」,也就是说要查两个 B+ 树才能查到数据。不过,当查询的数据是主键值时,因为只在二级索引就能查询到,不用再去聚簇索引查,这个过程就叫作「索引覆盖」,也就是只需要查一个 B+ 树就能找到数据
同时为多个列建立索引,以多个列的大小作为排序规则,比方说想让B+树按照c2列和c3列的大小进行排序
以c2、c3列的大小为排序规则建立的B+数称为联合索引,其本质上也是一个二级索引,但与分别为c2、c3列建立索引不同
B树索引适用存储引擎如表所示
| 索引/存储引擎 | MyISAM | InnoDB | Memory |
|---|---|---|---|
| B-Tree索引 | 支持 | 支持 | 支持 |
即使多个存储引擎支持同一种类型的索引,但是他们的实现原理不同
InnoDB、MyISAM默认的索引是Btree索引;Memory默认索引为Hash索引
MyISAM引擎使用B+Tree作为索引结构,叶子节点的data域存放 数据记录的地址

如果我们在Col2上建立一个二级索引,则此索引的结构如下图所示

MyISAM的索引方式都是“非聚簇的”,InnoDB中包含1个聚餐索引。
