MySQL——索引

发布于:2025-04-15 ⋅ 阅读:(24) ⋅ 点赞:(0)

一、索引基础:数据库查询的加速器

1. 什么是索引?

索引是MySQL中用于快速定位数据的一种数据结构,类似于书籍的目录。它通过建立数据与存储位置的映射关系,将随机查询转为有序查找,从而大幅提升查询效率。对于百万级以上的数据表,合理使用索引可使查询速度提升几个数量级。

2. 索引分类与创建示例

索引类型 特性说明 创建示例
主键索引 唯一且非空,每表仅一个 CREATE TABLE t (id INT PRIMARY KEY, name VARCHAR(20));
普通索引 无唯一性限制,加速普通列查询 CREATE INDEX idx_name ON t(name);
唯一索引 列值唯一但可为NULL CREATE UNIQUE INDEX uni_email ON t(email);
全文索引 针对文本内容的模糊搜索(需MyISAM/InnoDB引擎支持) CREATE FULLTEXT INDEX ft_content ON articles(content);
组合索引 多列联合索引,遵循最左前缀原则 ALTER TABLE t ADD INDEX idx_multi (col1, col2);

二、索引底层数据结构演进:从二叉树到B+树

1. 哈希表:适合等值查询

  • 原理:通过哈希函数计算键值存储位置,拉链法解决冲突。

  • 缺点:不支持范围查询,适合NoSQL场景(如Memcached)。

2. 有序数组:静态数据最优解

  • 原理:数据按序存储,二分查找效率高。

  • 缺点:插入/删除成本高,仅适合静态数据。

3. 二叉搜索树(BST)与平衡二叉树(AVL)

  • BST问题:极端情况下退化为链表(时间复杂度O(n))。

  • AVL优化:通过旋转保持左右子树高度差≤1,但频繁插入时维护成本高。

4. B-Tree与B+Tree:数据库索引的核心

  • B-Tree特点:多路平衡树,非叶节点存储数据。

  • B+Tree优化

    • 非叶节点仅存键值,叶节点双向链表连接。

    • 支持高效范围查询,减少磁盘IO次数。

    • InnoDB中,3层B+Tree可支撑千万级数据查询。


三、索引使用原则:高效查询的关键

1. 列的离散度:越高越好

  • 公式离散度 = COUNT(DISTINCT col) / COUNT(*)

  • 示例gender列(值0/1)离散度低,不适合单独建索引。

2. 组合索引的最左匹配原则

  • 规则:索引(a,b,c)生效场景:

    • WHERE a=?

    • WHERE a=? AND b=?

    • WHERE a=? AND b=? AND c=?

  • 失效场景

    • WHERE b=?(缺少最左字段)

    • WHERE a=? AND c=?(中间字段断裂)

-- 有效索引使用
EXPLAIN SELECT * FROM user WHERE name='张三' AND phone='13800138000';

-- 无效索引使用(未命中最左字段)
EXPLAIN SELECT * FROM user WHERE phone='13800138000';

3. 索引创建最佳实践

  • 推荐操作

    • 高频查询条件列优先建索引。

    • 使用前缀索引减少存储空间(ALTER TABLE t ADD INDEX idx (col(10)))。

    • 联合索引替代多个单列索引。

  • 避免操作

    • 在低离散度列(如性别)建索引。

    • 使用函数或表达式操作索引列(WHERE YEAR(create_time)=2023)。

    • 无序值(UUID)作为主键,导致页分裂。


四、索引失效场景:绕过性能陷阱

1. 隐式类型转换

-- 失效:name为字符串类型,与数值比较触发转换
EXPLAIN SELECT * FROM user WHERE name=136;

-- 有效:明确类型匹配
EXPLAIN SELECT * FROM user WHERE name='136';

2. 前导通配符模糊查询

-- 失效:以%开头无法使用索引
EXPLAIN SELECT * FROM articles WHERE content LIKE '%数据库%';

-- 有效:前缀匹配可走索引
EXPLAIN SELECT * FROM articles WHERE content LIKE '数据库%';

3. 索引列参与计算

-- 失效:对索引列进行运算
EXPLAIN SELECT * FROM orders WHERE total_price+100 > 2000;

-- 优化:将计算移至右侧
EXPLAIN SELECT * FROM orders WHERE total_price > 1900;

五、总结:索引优化的核心策略

  1. 理解数据结构:B+Tree的存储特性决定索引设计方向。

  2. 遵循最左原则:组合索引字段顺序需匹配查询模式。

  3. 监控离散度:优先为高区分度列建索引。

  4. 规避失效场景:避免函数、隐式转换和前导%模糊查询。

  5. 权衡代价:索引会降低写性能,频繁更新的表需谨慎。


网站公告

今日签到

点亮在社区的每一天
去签到