为什么MySQL会选错索引,如何解决?

本文涉及的产品
RDS PostgreSQL Serverless,0.5-4RCU 50GB 3个月
推荐场景:
对影评进行热评分析
云原生数据库 PolarDB 分布式版,标准版 2核8GB
云数据库 RDS SQL Server,基础系列 2核4GB
简介: InnoDB索引选择由优化器基于成本决策,受基数性、选择性、索引覆盖等因素影响。统计信息不准或复杂查询可能导致选错索引,可通过ANALYZE TABLE更新统计、FORCE INDEX强制索引或优化查询和配置来解决。

即使我们为表添加了索引,查询语句最终也不一定会使用索引,因为 InnoDB 是否使用索引、使用哪个索引是由优化器决定的。

SQL 优化器会分析所有可能的执行计划,并根据成本(代价)预估进行选择,倾向于选择成本最低的查询方式。这种优化器称为 CBO(基于成本的优化器)。

那么所谓的代价或成本主要与以下几个因素有关:

  1. 基数性
    索引的基数性通常指区分度,表示索引中不同取值的数量。基数性越高,索引的区分度越好,优化器越倾向于使用该索引。
  2. 选择性
    选择性反映索引过滤数据的能力。高选择性意味着索引能过滤掉更多的数据行,优化器更倾向于选择此类索引。该因素是决定扫描行数的关键,选择性越高的索引扫描行数越少。
  3. 索引覆盖
    如果查询所需的所有列都包含在索引中,即可完全通过索引获取数据,优化器会倾向于使用该“覆盖索引”,避免回表操作。
  4. ORDER BY
    当查询中包含 ORDER BY 子句时,如果排序字段上有索引,优化器为了减少文件排序(file sort),会更愿意使用该索引,因为索引本身具有顺序性。
  5. 索引类型
    不同类型的索引(如 B-TREE、HASH、FULLTEXT 等)适用于不同查询场景,优化器会根据查询类型选择最合适的索引。
  6. JOIN 类型和顺序
    对于包含 JOIN 的查询,优化器会综合考虑使用哪些索引以及 JOIN 的执行顺序。
  7. 索引的大小和深度
    较小、深度较浅的索引通常更快,因为占用磁盘空间少,能更快加载到内存中。
  8. 访问类型
    不同的访问方式,如范围查询、点查找或全表扫描,也会影响索引选择。例如某些索引结构更适用于范围查询。
  9. 内存使用
    对于大型表,优化器会评估执行计划的内存占用情况,尽量避免过度消耗内存。
  10. 系统资源限制
    优化器还会结合系统实际资源限制,如内存和磁盘 I/O 能力,进行执行计划选择。
  11. 查询缓存
    如果启用了查询缓存,且相同查询的结果已被缓存,优化器会直接使用缓存结果,而不再重新选择索引。

这里面比较重要的因素就是索引的基数性(区分度)、索引的选择性(扫描行数)、是否有索引覆盖等这几个。

由于索引选择是由以上多种因素共同决定的,因此最终选错索引可能由以下原因导致:

  1. 不准确的统计信息
    InnoDB 存储引擎依赖统计信息(如基数性、选择性等)来决定使用哪个索引。如果这些统计信息过时或不准确,优化器可能做出错误决策。
  2. 复杂的查询逻辑
    对于包含多表 JOIN、子查询、函数等复杂查询,优化器可能难以准确判断哪个索引最为有效。
  3. 系统和配置因素
    MySQL 的配置设置和系统资源限制(如内存大小)也会影响优化器的决策。

那么,如果发现 MySQL 选择了一个错误的索引,一般来说有以下几种解决方式:

  1. 更新统计信息
    定期运行 ANALYZE TABLE 命令来更新表的统计信息。这可以帮助优化器更准确地评估各个索引的有效性。
  2. 使用强制索引(FORCE INDEX)
    如果我们确定某个索引比优化器选择的更有效,可以在查询中使用 FORCE INDEX 来强制使用特定索引。
    如:SELECT * FROM clay_test_table FORCE INDEX (idx_name) WHERE name = 'CLAY';
  3. 但是,FORCE INDEX 应该谨慎使用,因为强制使用特定的索引可能会导致性能下降,特别是当表的数据分布发生变化时。在使用之前,应该确保理解该索引为什么是最好的选择,并且定期评估其效果。
  4. 优化查询
    简化查询逻辑,尽量避免复杂的连接和子查询,这有助于优化器做出更好的决策。
  5. 调整索引
    我们可以为 WHERE 条件中的过滤条件创建更合适的索引,并尽可能考虑创建复合索引来提高查询效率,尤其是对于多列的过滤和排序。
  6. 调整 MySQL 配置
    根据系统的资源和需求调整 MySQL 的配置参数,比如缓冲池大小(innodb_buffer_pool_size)。
目录
相关文章
|
5天前
|
数据采集 人工智能 自然语言处理
3分钟采集134篇AI文章!深度解析如何通过云无影AgentBay实现25倍并发 + LlamaIndex智能推荐
结合阿里云无影 AgentBay 云端并发采集与 LlamaIndex 智能分析,3分钟高效抓取134篇 AI Agent 文章,实现 AI 推荐、智能问答与知识沉淀,打造从数据获取到价值提炼的完整闭环。
393 93
|
6天前
|
域名解析 人工智能
【实操攻略】手把手教学,免费领取.CN域名
即日起至2025年12月31日,购买万小智AI建站或云·企业官网,每单可免费领1个.CN域名首年!跟我了解领取攻略吧~
|
6天前
|
SQL 人工智能 自然语言处理
Geo优化SOP标准化:于磊老师的“人性化Geo”体系如何助力企业获客提效46%
随着生成式AI的普及,Geo优化(Generative Engine Optimization)已成为企业获客的新战场。然而,缺乏标准化流程(Geo优化sop)导致优化效果参差不齐。本文将深入探讨Geo专家于磊老师提出的“人性化Geo”优化体系,并展示Geo优化sop标准化如何帮助企业实现获客效率提升46%的惊人效果,为企业在AI时代构建稳定的流量护城河。
395 156
Geo优化SOP标准化:于磊老师的“人性化Geo”体系如何助力企业获客提效46%
|
5天前
|
数据采集 缓存 数据可视化
Android 无侵入式数据采集:从手动埋点到字节码插桩的演进之路
本文深入探讨Android无侵入式埋点技术,通过AOP与字节码插桩(如ASM)实现数据采集自动化,彻底解耦业务代码与埋点逻辑。涵盖页面浏览、点击事件自动追踪及注解驱动的半自动化方案,提升数据质量与研发效率,助力团队迈向高效、稳定的智能化埋点体系。(238字)
282 158
|
13天前
|
机器人 API 调度
基于 DMS Dify+Notebook+Airflow 实现 Agent 的一站式开发
本文提出“DMS Dify + Notebook + Airflow”三位一体架构,解决 Dify 在代码执行与定时调度上的局限。通过 Notebook 扩展 Python 环境,Airflow实现任务调度,构建可扩展、可运维的企业级智能 Agent 系统,提升大模型应用的工程化能力。