共计 2165 个字符,预计需要花费 6 分钟才能阅读完成。
首先,什么是索引?咱们假如上面一个场景,当你拿到一本很厚的工具书进行有目标的查找内容的时候,你会怎么做?你必定不会对着这本书从头到尾地去找你想要找的内容(尽管这肯定也能够找到),因为这太消耗工夫了。你会做的必定是先查找书本的目录,找到你想要浏览的章节的页码,而后再到对应的页码去查找你想要的具体的内容,这显然是一种快得多的计划,特地是在书本的页数十分多的状况下。同理,数据库的索引表演的就是一种相似与目录的角色,它通过应用一些非凡的数据结构对数据库的数据进行一些非凡的排列,使得当咱们在依照肯定的要求查找数据的时候可能取得更快的相应。
一、索引的类型
B-Tree 索引
B-Tree 索引是以后应用最宽泛的一种索引的模式,他的底层实现其实是一种叫 B +Tree 的数据结构,这是一种非凡的树型数据结构。首先咱们看看 B +Tree 在索引中是怎么样进行实现的:
能够看到是一种相似于排列树的状况,即每一个节点都会保留一个数据,而这个节点的左子树保留的数据都要比以后的节点的值要小,右子树保留的数据都要比以后的节点的值要大。其实就是通过树形构造对数据进行了依照肯定规定的排列。指的留神的是,所有的叶子结点之间都有指针相互连接,不便数据的查找。
这样对数据进行解决的益处在于当咱们进行数据的查找时,不须要再对全表进行扫描了,只须要对索引的这棵树从根节点开始进行若干次的比拟,达到叶子结点再依据指针指向,找到咱们所要查找的数据。 留神此时,咱们进行比照判断的是索引树中的数据,而不是表中的数据。
咱们举一个例子来看看具体的实现。
mysql> CREATE TABLE People(last_name varchar(50) not null,
first_name varchar(50) not null,
dob date not null,
gender enum('m','f') not null,
key(last_name,first_name,dob)
);
下面的 sql 语句创立了一个表,并且对表中的 last_name,first_name 和 dob 列生成了索引:
咱们能够看到这个索引中的数据就会依照咱们给定的要求,对 last_name,first_name 和 dob 三列进行排序存储,值得注意的是,咱们察看途中最右下角的两个数据节点,会发现他们的 last_name,first_name 列的内容都是一样的,便依照 dob 进行排序,即对于一个多列的索引,排序也是有优先级的,这个优先级就是咱们在定义索引的时候的程序。
而如果在一个应用了 B -Tree 索引,咱们应用怎么的查问形式可能反对呢?
能够应用 B -Tree 索引的查问类型:
- 全值匹配
全值匹配指的是和索引中的所有列进行匹配,如上述条件中,查找一个姓名为 Cuba Allen,出生于 1960-01-01 的人。
- 匹配最左前缀
即对索引的第一列进行查找,下面例子的索引的第一列是 last_name,比方咱们要查找一个姓为 Allen 的人。
- 匹配列前缀
也能够只匹配某一列的结尾局部,如查找一个姓结尾为 J 的人,这里也应用了索引的第一列。
- 匹配范畴值
例如咱们能够查找,姓为 Allen 和 Barrymore 之间的人,这里也应用了索引的第一列。
- 准确匹配某一列,范畴匹配另外一列
咱们能够查找姓为 Allen,名是 K 结尾的人,即索引第一列全匹配,第二列范畴匹配。
B-Tree 索引的一些限度:
- 如果不是依照最左列进行查找,则无奈应用索引
例如,上述索引无奈用于匹配名字为 Bill 的人,这种状况下会进化为全表扫描。
- 不能跳过索引中的列
例如,上述索引无奈用于匹配一个姓为 Allen 且生日在 1960-01-01 的人,即必须依照从左到右的程序对索引的列进行匹配,不能两头跳过。
- 如果对索引中的一个列进行范畴查找,则它左边的列都无奈利用索引进行匹配
如后面例子中咱们匹配一个查找姓为 Allen,名是 K 结尾的人,因为 first_name 曾经是范畴匹配了,因而它左边的 dob 列就无奈利用索引了。
咱们从上述的限度能够看出,对于 B -Tree 索引,索引的程序会对这个索引的作用的施展和咱们查问语句的书写有着十分大的影响。
哈希索引
哈希索引蕴含两个数据,一个是哈希值,一个是指向数据行的指针。哈希值是通过数据的每一列进行哈希计算得出的。因而每一行的数据都有一个举世无双的哈希值。因为哈希索引只存储哈希值,因而构造能够存储得比拟紧凑,也因而进步了哈希索引的速度。
然而哈希索引也有它的限度:
- 哈希索引的数据是依照哈希值排列的而并不是依照数据自身排列的,因而不能用于排序。
- 哈希索引不反对局部索引列的匹配。因为哈希值是依据数据的每一列计算得出的,要失去哈希值就必须要有全副索引列的数据,因而如果一个数据有 A,B 两列,此时只有一个数据 A 是无奈通过哈希索引匹配到相干的数据的。
- 哈希索引只反对等值比拟,不反对范畴查问。
- 当呈现哈希抵触(即多个数据计算出来的哈希值雷同)的时候,这些数据以链表的模式存储在对应的哈希值下。
- 哈希抵触很多的时候,会对哈希索引的效率造成比拟大的影响,特地是在要删除一行数据的时候。
二、索引的长处
索引能够让服务器疾速定位到咱们须要的表的地位。但这并不是索引带来的惟一的益处。总结下来索引的长处次要有以下三个:
- 索引大大减少了服务器须要扫描的数据量
- 索引能够帮忙服务器防止排序和长期表
- 索引能够将随机 I / O 变为程序 I /O