MySQL索引的概念
索引是一种数据结构,用于快速查找数据库表中的记录。通过在列上创建索引,可以提高检索数据的速度,减少查询所需的时间。索引类似于书籍的目录(或者字典),可以帮助数据库系统快速定位到需要的数据行,而不必逐行扫描整个表。
需要注意的是,虽然索引可以提高查询效率,但过多的索引也会增加数据库的存储空间和维护成本,同时会影响插入、更新和删除操作的性能。因此,在创建索引时需要权衡各方面的因素,选择适合的索引策略来优化数据库性能。
为什么说索引会影响插入、更新和删除的性能呢?
每个索引都会存储索引列的数值及指向实际数据行的指针,这些额外的存储空间会占据一定的存储资源。当表中存在多个索引时,这些额外的存储开销会逐渐累积,导致整体数据库的存储空间增加。
而维护成本方面,当对表进行插入、更新和删除操作时,数据库系统需要维护索引的结构以保证数据的一致性和准确性。每次数据的修改都可能导致相关索引的更新,特别是对于涉及索引列的操作,这会增加数据库系统的负担和开销。如果表中存在多个索引,那么每次数据修改都可能导致多个索引的更新,从而增加了操作的时间消耗。
索引相关的语法记录
table_name 等于要查询的表名
index_name 等于索引名称
column_name 是字段/列
- 查看指定表的索引信息:SHOW INDEX FROM tabke_name
- 查看sql执行计划: EXPLAIN SELECT * FROM table_name 直接在查询语句前加EXPLAIN
- 删除索引的方法:
常见的索引的类型
-
普通索引(Normal Index):最基本的索引类型,没有任何限制。
创建一个普通的索引:CREATE INDEX index_name ON table_name (column_name);
-
唯一索引(Unique Index):索引列的值必须是唯一的,用于确保数据的唯一性。
创建一个唯一索引:CREATE UNIQUE INDEX index_name ON table_name (column_name);
-
主键索引(Primary Key Index):主键索引是一种唯一索引,不允许NULL值,并且表中只能有一个主键索引。主键索引通常用来唯一标识表中的每一行数据。
-
组合索引(Composite Index):将多个列组合起来创建的索引,适用于需要同时查询多个列的情况。组合索引可以提高多列查询的性能。
-
全文索引(Fulltext Index):用于全文搜索的索引类型,适用于对文本数据进行搜索操作。
创建全文索引:ALTER TABLE table_name ADD FULLTEXT index_name (column_name);
-
空间索引(Spatial Index):用于地理空间数据的索引,支持空间数据类型的快速检索和空间关系运算
使用 CREATE SPATIAL INDEX
语句来创建空间索引
-
B-tree 索引:(Balanced Tree)索引是最常见和默认的索引类型。它适用于范围查找和排序操作,能够快速定位到目标数据。B-tree 索引适用于等值查询、范围查询和排序操作。
MySQL 中的普通索引默认就是 B-tree 索引。B-tree(Balanced Tree,平衡树)是一种常见的数据结构,用于实现数据库中的索引。在 MySQL 中,创建普通索引时,如果不指定索引类型,默认情况下会创建一个 B-tree 索引。
-
哈希索引:哈希索引使用哈希算法将索引列的值映射为哈希值,然后通过哈希表快速查找数据。哈希索引适用于等值查询,但不支持范围查询和排序操作。
创建一个哈希索引:CREATE INDEX index_name ON table_name (column_name) USING HASH;
索引失效的原因
索引列参与运算:
- 原因:索引列参与了运算,导致索引无法被使用。
- 例子:
SELECT * FROM products WHERE price + discount = 100;
如果price
和discount
都有索引,但由于参与了运算,索引失效。
隐式类型转换:
- 原因:查询条件中的列类型与索引列的类型不匹配,数据库进行了隐式类型转换,导致索引失效。
- 例子:
SELECT * FROM employees WHERE id = '100';
如果id
是整数类型的列,但查询条件中使用了字符串,索引失效。
模糊查询通配符位置不当:
- 原因:通配符(如
%
)出现在查询条件的开头,导致索引无法被利用。 - 例子:
SELECT * FROM customers WHERE name LIKE '%Smith';
查询以%
开头的模糊查询会导致索引失效。
最左匹配原则的原理
MySQL 建立多列索引(联合索引)有最左匹配的原则,即最左优先:
如果有一个 2 列的索引 (a, b),则已经对 (a)、(a, b) 上建立了索引;
如果有一个 3 列索引 (a, b, c),则已经对 (a)、(a, b)、(a, b, c) 上建立了索引;
待完善~~~~~~~