2025年12月07日/ 浏览 21
正文:
在数据库优化中,索引是提升查询性能的核心手段之一。而联合索引(又称复合索引或多列索引)因其能够覆盖多个查询条件,成为高频场景下的利器。但若使用不当,反而会成为性能瓶颈。本文将系统讲解联合索引的创建方法、底层原理及实战注意事项。
MySQL中创建联合索引的语法非常简单,通过ALTER TABLE或CREATE INDEX即可实现:
-- 创建表时直接定义联合索引
CREATE TABLE articles (
id INT PRIMARY KEY,
title VARCHAR(100),
author VARCHAR(50),
publish_time DATETIME,
KEY idx_title_author (title, author)
);
-- 已有表追加联合索引
ALTER TABLE articles ADD INDEX idx_author_time (author, publish_time);
CREATE INDEX idx_title_time ON articles(title, publish_time);
关键点:
1. 索引命名建议体现列顺序(如idx_title_author);
2. 单表索引数不宜过多(通常不超过5个),避免写性能下降。
联合索引的本质是一棵B+树,其键值按声明顺序拼接。例如索引(title, author):
– 数据按title排序,title相同时按author排序;
– 查询时若跳过title直接查author,索引会失效(最左前缀原则)。
示例场景:
-- 有效使用索引(命中title)
SELECT * FROM articles WHERE title = 'MySQL优化' AND author = '张三';
-- 索引失效(未使用最左列title)
SELECT * FROM articles WHERE author = '张三';
联合索引必须从最左列开始使用,否则无法命中。例如索引(A,B,C):
– 有效组合:A、A,B、A,B,C;
– 无效组合:B、C、B,C。
WHERE user_id=1 AND status=2,优先(user_id, status); WHERE YEAR(publish_time)=2023会导致索引失效; WHERE title=123; WHERE title='A' OR author='B'可能全表扫描。 若查询列全部包含在索引中,可避免回表操作:
-- 覆盖索引示例(只需查索引树)
SELECT title, author FROM articles WHERE title LIKE 'MySQL%';
假设有订单表orders,常见查询包括:
1. 用户ID+状态筛选;
2. 状态+创建时间范围查询。
优化方案:
-- 联合索引设计
ALTER TABLE orders ADD INDEX idx_user_status (user_id, status);
ALTER TABLE orders ADD INDEX idx_status_time (status, create_time);
效果对比:
– 原查询WHERE status=2 AND create_time>'2023-01-01'耗时200ms;
– 增加索引后降至5ms。
联合索引是一把双刃剑,合理设计可提升查询效率数倍,而错误使用则可能导致性能劣化。牢记以下原则:
1. 最左匹配是铁律;
2. 列顺序需权衡查询频率和区分度;
3. 警惕索引失效的语法陷阱;
4. 善用覆盖索引减少IO。