数据库索引到底是个什么东西?
很多同学都知道,在数据库表的一些字段上建立索引会使SQL语句的执行速度变快,但是对于索引不明白具体是什么东西,这一章我们就从索引的概念开始来了解一些相关的知识。
举个栗子:
在生活中,通过查询书的目录来确定某一章节在多少页是我们都有的经历,但是同学们有没有想过,为什么通过查询目录就会很快速的定位到某一章节在多少页,目录提升检索效率的本质是什么?
我们来看这个问题,假如有一本页数有2000页并且没有目录的书给大家阅读,当我们想查找某一章节在多少页,我们会在这2000页里一页一页进行翻阅查找,当最坏情况发生时,我们需要将这俩千页都翻一遍才能找到,这样花费的时间是我们不能接受的。
如果我们此时将这本书的章节标题和对应的页码都排列在一起生成一张目录,假设这张目录一共4页长,当我们再去查询某一章节在哪页的时候,是不是最坏情况也只需要翻查这4页目录的内容就可以找到对应的页码,这样一比较,是不是发现我们查找的页数量变小了非常多,这使得我们的查询变得非常迅速。所以目录的出现减少了我们需要查询内容的大小。
当我们有了这样的一张目录时,我们还可以考虑将目录优化一下来让我们进行更快速的查询,比如:对页码进行排序。
这样排序后的目录是不是就更方便我们进行查找?
相同的道理,当我们数据库表中的数据非常大量时,我们也希望能将数据库表中一些高离散性(重复率低的)的字段做成目录,通过查询目录来快速定位到某一条数据的位置,避免对整张表的数据进行一条一条的检索工作,这种在数据库的目录就是我们说的索引。
与对页码进行排序的思想相同,我们也会对索引的存储方式进行更好的优化,来提供我们对目录的检索效率。
维基百科对数据库索引的定义是:
数据库索引,是数据库管理系统(DMBS)中一个排序的数据结构,以协助快速查询、更新数据库表中数据。
我们以一张user表,在user_id这个字段上建立索引为例在理解一下索引:
我们将定义说成大白话,就是我们会把user表中user_id的值都取出来,排序后放在一个特定的数据结构里,我们把这个放入了user_id的数据结构叫做user_id的索引。我们以后再需要用 user_id=1 作为查询条件进行查询时,就可以通过索引来快速定位user_id=1的这条数据在哪里,这样就可以对数据进行高效的查询,避免了在整张表全表检索user_id=1的数据。
所以索引的本质就是我们以某些字段建立一个类似目录的东西,让我们能够快速定位到数据所在的位置。
到这里我们还要明确一点:索引的实现方式有很多种,并不唯一。
我们要清楚,在不同的应用场景里,不同方式实现的索引会发挥出不同效率的查询速度,所以对于Mysql各个数据引擎来讲,也会有不同的实现方式,比如像下图这种方式实现索引。
当我们对索引有了一定的概念后,我们需要思考的问题就是:
到底什么样的数据结构,才能满足索引的快速查找定位的功能呢?
下一篇文章我们来聊一下,InnoDB与MyIsam存储引擎的索引数据结构到底是怎么推演得来的。