1.1 概念
索引是一种特殊的文件,包含着对数据表里所有记录的引用指针。可以对表中的一列或多列创建索引, 并指定索引的类型,各类索引有各自的数据结构实现。
1.2 作用
数据库中的表、数据、索引之间的关系,类似于书架上的图书、书籍内容和书籍目录的关系。 索引所起的作用类似书籍目录,可用于快速定位、检索数据。 索引对于提高数据库的性能有很大的帮助。
1.3 使用场景
要考虑对数据库表的某列或某几列创建索引,需要考虑以下几点:
- 数据量较大,且经常对这些列进行条件查询。
- 该数据库表的插入操作,及对这些列的修改操作频率较低。
- 索引会占用额外的磁盘空间。
满足以上条件时,考虑对表中的这些字段创建索引,以提高查询效率。 反之,如果非条件查询列,或经常做插入、修改操作,或磁盘空间不足时,不考虑创建索引。
举一个形象的例子,索引本质上相当于“书的目录”,通过目录就可以快速的找到章节对应的位置,索引的效果就是加快了查找的速度。
数据库操作查的概率比增删改的概率要大得多,因此大多数情况下,引入索引还是比较好的选择,但是注意,索引也会增加增删改的时间开销(增删改需要调整已经创建好的索引目录),还会增加空间的开销(构造索引,也需要额外的硬盘空间来保存)。
1.4 使用
mysql数据库创建主键约束(PRIMARY KEY)、唯一约束(UNIQUE)、外键约束(FOREIGN KEY)时,会自动创建对应列的索引。
- 查看索引——show index from 表名;
- 创建索引:对于非主键、非唯一约束、非外键的字段,可以创建普通索引——create index 索引名 on 表名(字段名);
- 删除索引——drop index 索引名 on 表名;
创建索引最好是在表创建之初就把索引给搞好,否则在数据很多的情况下是很危险的操作。
- 吃掉大量的磁盘IO,这段时间内数据库是无法被正常运行的(删除索引也是如此)
- 针对性别这样的列添加索引是无法提高查找数据的
- 要是已经有大量数据了,再进行操作就要慎重了
索引创建好之后不需要手动使用,直接查询的时候数据库会自动的来走索引,SQL是通过数据库的执行引擎来执行的,执行引擎内部会有优化操作(自动评估,选择成本最低,速度最快的方法),查询是否在走索引或者怎么走的是不好预测的,可以使用explain这个关键词来显示查询过程中具体的使用索引的情况。
索引在mysql中的数据结构
是哈希表吗? 不是
哈希表只能比较相等,无法进行范围查询(显然mysql经常要范围查询)
是二叉搜索树吗? 不是
二叉可以范围查询,但元素个数多了树的高度会很高,元素的比较次数就会比较多
是N叉搜索树(B树)吗? 不是
虽然比较次数较二叉没怎么减少,但是读写硬盘的次数减少了
是B+树吗? 是滴~
为数据库量身定做的数据结构
- B+树也是一个N叉搜索树,每个节点上可能包含N个key,N个key划分出N个区间,最后一个key相当于是最大值。
- 父元素的key会在子元素中重复出现,并且是子元素中的最大值(这样重复出现导致叶子节点包含了所有数据的全集,非叶子节点中的所有值都会在叶子节点中体现出来)
- 叶子节点用类似链表的方式首尾相连
B+树的优点:
- 作为一个N叉树,高度降低了,比较的时候硬盘IO次数减少了
- 更适合进行范围搜索
- 所有的查询都是要落在叶子节点上的,所以无论查询哪个元素,中间比较的次数差不多,查询操作比较均衡
- 由于所有的key都会在叶子节点中体现,因此非叶子节点不必存表的真实数据(数据行),只需要把所有的数据行给放到叶子节点上即可(非叶子节点只需要存索引列的值)
非叶子节点中只存了简单的id,所以空间成本大大降低,可以在内存中缓存,提高查询速度,减少硬盘IO次数。
B+树这个结构只是针对mysql的InnoDB这个数据库引擎里面所典型使用的数据结构。(不同的数据库所使用的数据结构也是不同的)