MysqL 哪些情况适合创建索引

文章目录

一、高频出现在 WHERE 条件中的字段

这是索引最核心、最常用的场景。

为什么适合

查询时,如果字段没有索引,就必须逐行扫描整张表(全表扫描);

有了索引,就能通过 B+ 树快速定位到符合条件的行,数据量越大提速越明显。

典型例子

  • 业务中经常按「员工姓名」「邮箱」「部门ID」查员工信息,这些字段就适合建索引。
  • 对应你的 employees 表:department_idjob_id 这类经常作为筛选条件的字段,建索引就是合理的。

重要补充

如果多个字段经常组合在一起做查询条件 ,优先建联合索引 ,而不是给每个字段单独建单列索引。

比如,经常用 name + age 筛选,建 idx_name_age(name, age) 的收益,远高于两个单列索引。


二、JOIN 关联查询中的关联字段(外键字段)

联表查询的关联字段,几乎是必建索引的场景。

为什么适合

两张表关联查询时

(比如 employees JOIN departments ON employees.department_id = departments.id),

如果关联字段没有索引,每次关联匹配都要做一次全表扫描,数据量上来后性能会极差。

典型例子

你的 employees 表里的 department_idjob_idmanager_id 都属于这类:

  • department_id 关联部门表
  • job_id 关联职位表
  • manager_id 关联上级员工(自连接)

这也是为什么你这张表的这三个字段都已经建了索引,是非常标准的建法。

注意

关联字段的类型、长度、字符集必须完全一致 ,否则会触发隐式类型转换,导致索引失效


三、ORDER BY / GROUP BY 后面的字段

排序 和 分组,是索引的第二大适用场景。

为什么适合

B+ 树索引本身就是排好序的结构:

  • ORDER BY:直接用索引的顺序输出,不用再做「文件排序(Using filesort)」,速度提升非常明显
  • GROUP BY:索引有序,分组时不用再生成临时表(Using temporary),避免额外的内存/磁盘开销

典型例子

  • 经常按「入职时间倒序」查询员工列表 → hire_date 适合建索引
  • 经常按「部门分组统计人数」 → department_id 适合建索引

补充技巧

如果查询同时有 WHEREORDER BY,优先建联合索引 ,把 WHERE 字段放最左边,排序字段放后面,符合最左前缀原则,既能过滤又能排序。

比如:WHERE department_id = 10 ORDER BY hire_date

idx_dept_hire(department_id, hire_date)


四、区分度高的字段(Cardinality 大)

索引的效率,很大程度取决于字段的「区分度」。

为什么适合

区分度越高,索引一次能过滤掉的数据就越多,查询效率提升越明显;

反之,如果字段值大量重复,索引过滤不了几行,优化器会觉得还不如全表扫,直接放弃索引。

判断标准

SHOW INDEX 里的 Cardinality 值,值越接近表总行数,区分度越好。

  • ✅ 适合:邮箱、工号、身份证号,几乎不重复,区分度拉满
  • ❌ 不适合:性别、状态(只有 0/1 两种值)、是否删除等低基数字段

对应你的表

  • employee_idemail 基数 107,和表总行数一致 → 区分度极好,建索引收益最高
  • department_id 基数 12 → 区分度一般,数据量小的时候还行,百万级数据下收益会很低

五、需要保证唯一性的业务字段

业务上要求不重复的字段,直接建唯一索引,一举两得。

为什么适合

  1. 数据约束:由数据库层面保证字段值不重复,比代码判断更可靠,能避免并发导致的重复数据
  2. 查询加速:唯一索引同时具备普通索引的所有加速能力,等值查询性能极高

典型例子

  • 员工邮箱、工号、身份证号
  • 对应你表里的 emp_email_uk,就是非常标准的唯一索引设计

六、适合做「覆盖索引」的高频查询

这是进阶优化场景,用得好性能提升非常显著。

为什么适合

如果一条查询要取的字段,在索引里就全部包含了,就不需要回表去聚簇索引里查完整数据,直接从二级索引里就能拿到结果,这就是覆盖索引,省去了回表的IO开销。

典型例子

业务高频执行:

sql 复制代码
SELECT name, age 
FROM employees 
WHERE name = '张三';

建联合索引 idx_name_age(name, age),查询时直接从索引里取 name 和 age,完全不用回表,

性能接近主键查询。


反向补充:这些情况不建议建索引

知道什么时候建,也要知道什么时候别乱建:

  1. 数据量很小的表(几百几千行):全表扫描比走索引还快,建了反而浪费空间
  2. 写操作远多于读操作的表:增删改都要维护索引,会大幅拖慢写入性能
  3. 区分度极低的字段(如性别、状态):索引收益几乎为0
  4. 频繁更新的字段:索引维护成本很高
  5. 冗余、重复的索引 :比如你表里的 emp_emp_id_pk,和主键索引完全重复,纯纯浪费空间

新手建索引优先级参考

按重要性从高到低:

  1. 主键(自动创建,不用管)
  2. 业务唯一键 → 建唯一索引
  3. 所有 JOIN 关联字段 → 建普通索引
  4. 高频出现在 WHERE 中的字段 → 按需建单列/联合索引
  5. 经常排序、分组的字段 → 结合 WHERE 建联合索引
  6. 高频慢查询 → 用覆盖索引做专项优化
相关推荐
时间的拾荒人1 小时前
MySQL C语言连接 - 从入门到实战
android·c语言·mysql
Database_Cool_3 小时前
云数据库控制台好不好用、能不能可视化操作:阿里云 RDS MySQL 控制台体验详解
数据库·mysql·阿里云
番茄炒鸡蛋加糖4 小时前
MySQL 实战调优& 分表基础
数据库·mysql
万亿少女的梦1684 小时前
基于Spring Boot的游戏交易管理系统设计与实现
java·spring boot·mysql·系统设计·交易管理
Database_Cool_4 小时前
云数据库如何保证高可用、故障了怎么办:阿里云 RDS MySQL 高可用架构详解
数据库·mysql·阿里云
Mem0rin5 小时前
[MySQL] 聚合函数、分组查询、连接查询
android·mysql
一棵星5 小时前
内网 MySQL 表结构一键导出 Word 文档:直连 + Agent 双模式实战
数据库·mysql·word
会编程的土豆6 小时前
数据库 mysql篇 八股2
数据库·mysql·八股
IT小盘7 小时前
08-FastAPI加MySQL实现AI对话记录持久化
android·mysql·fastapi