当前位置: 首页 > news >正文

覆盖索引:让你的查询直接从索引返回,彻底告别回表

​关键词​覆盖索引回表复合索引EXPLAIN深分页优化MySQL优化Using index大家好我是小耶写功课只是为了我踩过的坑你们别再踩了聊到索引优化很多人知道“建索引”但不知道“怎么建才能让查询最快”。今天讲一个进阶却非常实用的概念​覆盖索引​。用好它可以让你的查询直接从索引拿到数据连表都不需要回性能直接起飞。上周讲了窗口函数和CTE的性能对比有读者留言说那些优化确实好但自己遇到的慢查询大多还是索引没用对。没错索引是SQL性能的基石。覆盖索引是索引优化里“性价比”最高的技巧之一——不增加额外存储成本不改SQL逻辑只调整索引字段顺序就能减少一半的I/O。下面我们从原理开始一步步说清楚。覆盖索引是什么先回顾一下InnoDB索引的结构InnoDB使用B树索引对于二级索引非主键索引叶子节点存储的是​索引列的值 主键值​。当执行一个查询时如果索引里已经包含了查询需要的所有列InnoDB就可以直接从索引树的叶子节点拿到数据不需要再根据主键回主键索引查整行。这就叫​覆盖索引​。举个具体例子表orders有列order_id(主键)、user_id、order_amount、order_date。执行查询SELECT user_id, order_amount FROM orders WHERE user_id 12345。如果只在user_id上建索引InnoDB先在user_id索引上找到所有匹配的记录得到主键order_id列表然后根据每个order_id去主键索引回表取出order_amount。这需要「索引扫描行数 回表次数」次I/O。如果建复合索引(user_id, order_amount)InnoDB在复合索引上找到user_id12345的叶子节点叶子节点里已经包含了user_id和order_amount直接返回不需要回表。只需要「索引扫描行数」次I/O。性能提升通常在2~5倍回表成本越高提升越明显。如何判断你的查询是否用上了覆盖索引用EXPLAIN看执行计划Extra列出现**Using index**时说明用上了覆盖索引。注意Using index不是索引类型而是一种执行方式表示“不需要回表”。如果出现Using index condition说明用了索引下推ICP但仍需回表。如果出现Using where说明没有用覆盖索引。掌握这个判断方法之后你就可以主动检查自己的慢查询看看有没有机会通过调整索引来消除回表。深分页场景下的覆盖索引应用日常开发中经常遇到这样的分页查询SELECT id, name, age FROM users ORDER BY id LIMIT 100000, 10。直接这样写MySQL会先扫描前100010行包括回表然后丢弃前100000行只返回最后10行。当偏移量很大时这个操作非常慢。优化的思路是先用覆盖索引快速定位到要取的行的主键范围再回表取完整数据。具体写法SELECT u.id, u.name, u.age FROM users u JOIN (SELECT id FROM users ORDER BY id LIMIT 100000, 10) tmp ON u.id tmp.id;内层子查询SELECT id FROM users ORDER BY id LIMIT 100000, 10只用到了主键id主键索引天然就是覆盖索引执行非常快。外层再根据这10个id回表取完整数据只需要10次回表。这种方法称为“延迟关联”性能提升非常明显。使用覆盖索引需要注意什么覆盖索引虽然好用但也不是万能的有几个地方要留心​索引不是越宽越好​覆盖索引需要把查询中用到的列都放进索引这会增加索引的存储空间。而且索引越“胖”写入INSERT/UPDATE/DELETE时维护索引的成本就越高。只把查询中频繁出现的列放进去不要贪多。​**尽量避免SELECT ***​SELECT *基本不可能被覆盖因为索引一般不会包含所有列那样索引会巨大。尽量只查询需要的字段这不仅有利于覆盖索引也能减少网络传输。​字符串列要小心​如果查询中包含了长文本字段如VARCHAR(255)覆盖索引会变得很大可能得不偿失。这种情况下可以权衡是否值得做覆盖。总结覆盖索引是SQL优化工具箱中最趁手的工具之一。它不改变业务逻辑不增加额外的系统复杂度只是让索引设计得更“聪明”。下次写查询时先问问自己这个查询需要的所有列有没有可能全部放进一个索引里如果能性能提升会非常直观。小耶在手SQL 不愁还有什么想了解的欢迎留言小耶一定知无不言言无不尽……我们下次见~参考文献MySQL官方文档《Covering Indexes》《高性能MySQL》第4版第5章索引优化
http://www.zskr.cn/news/1390510.html

相关文章:

  • 从手机卡顿到单片机复位:聊聊STM32的NRST引脚和BOOT键背后的硬件逻辑
  • 别再为UDP分包头疼了!ESP32-CAM传图到Python服务端的完整数据拼接方案
  • RV1126开发板实战:手把手教你用AT指令驱动SIMCOM A7670C 4G模块上网(附完整C代码)
  • DIY智能窗户防盗警示装置:雷达与光敏传感器实现低成本安防
  • Kaggle免费GPU保姆级教程:从开启Internet到后台运行,新手避坑全记录
  • 2026科瑞昌工业空调:制造业降温三大核心趋势 - 速递信息
  • Honey Select 2终极汉化去码补丁:5分钟快速安装与完整功能指南
  • R语言数组(Array):多维数值计算的底层高效结构
  • 从DC到DCG:手把手教你配置Synopsys综合工具的物理约束(附DEF文件处理技巧)
  • 从STM32转战华大HC32F4A0:手把手移植NVIC,搞定TIM6 PWM捕获中断配置
  • 从零到一:在STM32F407上构建UCOS II实时操作系统
  • Azure Storage Explorer深度指南:Blob管理、SAS安全与跨区域复制实战
  • 3分钟搞定!Deepin Boot Maker:Linux新手也能轻松制作启动盘
  • Web安全零基础靶场搭建实战:pikachu与DVWA避坑指南
  • 2026年最新临邑黄金回收白银回收铂金回收靠谱店铺权威排行榜TOP5:纯金+金条+银条+钯金 门店地址联系方式推荐 - 莘州文化
  • Wand-Enhancer:三步解锁WeMod专业功能,打造个性化游戏体验
  • 如何用SMUDebugTool实现AMD锐龙深度调优:探索5种创新应用场景
  • ComfyUI IPAdapter Plus完整指南:3步实现图像风格迁移
  • 揭阳六大黄金回收门店|同城黄金回收服务,多门店联动便捷变现 - 润富黄金珠宝行
  • 别再只会apt install了!UOS/Deepin软件包管理命令大全(含dpkg、aptitude)
  • 别再自己造轮子了!用C#和netDxf库5分钟搞定DXF文件解析(附完整代码)
  • DeviceUtil 电源状态工具函数:HarmonyOS 应用如何感知设备电源模式
  • STM32G474四种编程范式对比:从HAL库到FreeRTOS的LED闪烁实战
  • 别再傻傻分不清了!一文搞懂TD-OCT和FD-OCT到底差在哪(附光源、探测器选择指南)
  • 2026年最新陵城黄金回收白银回收铂金回收靠谱店铺权威排行榜TOP5:纯金+金条+银条+钯金 门店地址联系方式推荐 - 莘州文化
  • ClusterGVis终极指南:三步完成基因表达矩阵聚类与可视化
  • 告别U盘安装Ubuntu的‘找不到介质’和ACPI报错:一个被忽略的USB协议兼容性问题
  • 面向对象CMDB架构:iTop企业级ITSM平台的高性能设计与生产就绪实践
  • Minecraft服务器三层纵深防护实战:iptables+JVM沙箱+SQLCipher加密
  • 泉州闲置黄金变现怕踩坑?福运来免费上门回收值得信赖 - 黄金回收