认识索引(二)

认识索引(二)

上一节我们简单的回答了索引是什么、常见的索引分类,以及简单的讲解了根据应用层次划分的各个索引。这一节,我们将会先从索引的基础理论知识开始讲起,也就是二分查找法、Hash和B+Tree.

简单回顾

​ Q: 简单说说什么是索引?

​ A:索引就是存储引擎用于快速查找数据记录的一种数据结构。需要额外开辟空间和数据维护。另外,索引是物理数据页存储,在数据文件中(innoDB,ibd文件),利用数据页(page)存储。索引可以加快检索的速度,但同时也会降低增删改的操作熟读,索引维护需要代价。

二分查找法

​ 其实绝大部分小伙伴绝对知道这个算法,因为这个可能曾经作为作业在OJ上敲过。虽然已经知道但还是要温习一下,温故而知新嘛。

​ 二分查找法也称为折半查找法,它成立的条件是原数组是有序的。

​ 二分查找的优点是等值查找、范围查找性能优秀,但是缺点也是很明显的,增、删、改数据的时候维护成本高。

​ 算法实现思路:

	1. 首先定位left和right两个指针
	2. 计算中间值middle,middle = (left + right)/ 2;
	3. 判断middle值和目标值的大小对比
	4. middle值大于目标值,那么right = middle-1;middle值小于目标值,left = middle + 1;

大家可以看下面简单的示例:有序数组是17个,目标值(要查找的)是7,过程如下:
在这里插入图片描述
在这里插入图片描述

2. Hash结构

​ Hash其实最底层就是Hash表。Hash表是键值对 key-value的存储结构,非常适合找一个值,也就是等值查询。
在这里插入图片描述

其实上面这个就是数组+链表的结构,而我更喜欢用以前数据结构书上的称呼---- 拉链法。

大家其实也能看出来,这样的Hash索引可以比较方便提供等值查询

但缺点也是非常明显的,也就是当你要查询一个范围内的值,也就是范围查询,那么你实际上就是分解成查了多次的等值查询,至于这个多次就取决你要查的范围的长度。这样相当于你是在做一个全表的查询,而我们的想法是,最好范围查就是能确定一个范围,然后尽可能少的查询,最好确定范围之后一次性遍历全弄出来。

Hash索引在Mysql中的Hash结构主要应用在两个地方,Memory原生的Hash索引 和 InnoDB自适应哈希索引。

这里InnoDB引擎主要使用的是自适应Hash索引,其实了解过Mysql内部结构的时候知道,Mysql中分成内存结构和磁盘结构,在内存结构中含有Buffer Pool、Change Buffer、Log Buffer 以及 Adaptive Hash Index(自适应哈希索引),下面这张图将会更清晰的看到(红箭头的部分就是自适应Hash索引)

在这里插入图片描述
InnoDB自适应Hash索引是为了提升查询的效率,因为InnoDB存储引擎会监控表上的各个索引页的查询,当InnoDB注意到某些索引值访问的比较频繁(也就是热点数据上索引),那么它会在内存中基于B+树索引再创建一个Hash索引。

这样让内存中的B+树索引具备Hash索引的功能,即能够快速定值访问被频繁访问的索引页。

一句话总结:InnoDB自适应索引就是 在使用Hash索引访问时,一次性查找就能定位数据,等值查询效率要优于B+树。

自适应Hash索引的建立使得InnoDB存储引擎能自动根据索引页访问的频率和模式自动地为某些热点页建立Hash索引来加速访问。

另外InnoDB自适应索引的功能,用户只能选择开启或者关闭功能,无法进行人工干涉。

show engine innodb status \G;
show variables like '%innodb_adaptive%';

3.B+Tree结构

​ Mysql数据库索引默认采用的是B+Tree结构,B+树其实在B树的结构上改进的。这里要进行一点说明,就是B树也被有些人称为B-树,其实这么说其实也没错,B-Tree和B+Tree一看,的确减号和加号,但其实原来的叫法的是B树,所以我下面就统一叫B树了。

3.1 B-Tree结构

​ B树其实是用来多路平衡查询的,所以也叫多路平衡查找树。

​ 下面是对B树的构成定义:
在这里插入图片描述
但因为今天主角不是B树,所以我们长话短说,直接上图,具体的分析一下B树:
在这里插入图片描述
上面是一棵B树,从观察看到,首先每一个节点都有索引值和数据,分布于整个树中。其次每一个节点可以存放索引值以及它对应的数据data。 另外,索引是升序排列的。

总结:

  • ​ 索引值和data数据分布在整棵树结构中。
  • ​ 每一个节点可以存放多个索引及对应的data数据。
  • ​ 树节点中的多个索引从左到右升序排列。

B树的搜索:从根节点开始,对节点内的索引值进行二分查找,如果命中那就结束查找。没有命中,就会到对应的子节点中查找,然后重复,直到所对应的指针为空,或者已经是叶子节点才结束。

其实这个时候已经实现了范围查询的能力,避免了全表数据的扫描,提升了查找的效率。但是效率还是太低,不适合应用于数据库索引,于是B+树出现了。

3.2 B+Tree结构

​ 直接上图,来看看一个简单的B+树结构:
在这里插入图片描述
观察B+树的结构,能清晰的看到非叶子节点没有data数据,只存储索引值,这样能存上更多的索引。而且范围查找,没有了data值得读取,减少磁盘IO。叶子节点包含了所有的索引值和data,并且用指针将其串联起来,提高了区间的访问性能。

总结:

  1. 非叶子节点只存索引值不存data,可以存更多的索引值
  2. 叶子节点包含了所有的索引和data值
  3. 叶子节点用指针连接,提高区间的访问能力

其实相比于B树,B+树进行范围查找的时候,只需要查找定位两个节点的索引值,然后利用叶子节点的指针进行遍历即可。而B树需要遍历范围内的所有节点(所有的索引和data数据),因为在树上遍历一个是,显然B+树的效率比较高。

有的同学可能不理解为什么B树遍历效率低于B+树,因为在本质上来讲B+树的叶子节点区间通过指针串联,导致B+树只需要遍历叶子节点就可以遍历整棵树,无限接近于一个链表的遍历了。而B树的遍历本质上还是一个树的遍历,树的遍历也就意味着非叶子极有可能被访问了多次。而在数据库中基于范围的查询是十分常见的,甚至可以说是极其频繁的,如果采用B树的话,效率将会极其低下(非常低)。

总结

在本文中,我们简单的回顾了一节的问题,什么是索引,以及在本节中简单的聊了聊在深入讲述索引之前的一些必备的理论知识,二分查找算法、Hash和B+Tree结构,那么在下一节中我们将会讲解聚簇索引和辅助索引,敬请期待。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值