首页 > 其他分享 >面试官:limit 100w,10为什么慢?如何优化?

面试官:limit 100w,10为什么慢?如何优化?

时间:2024-09-05 19:52:48浏览次数:11  
标签:10 面试官 查询 索引 limit 优化 ID

在 MySQL 中,limit X,Y 的查询中,X 值越大,那么查询速度也就越慢,例如以下示例:

  • limit 0,10:查询时间大概在 20 毫秒左右。
  • limit 1000000,10:查询时间可能是 15 秒左右(1秒等于 1000 毫秒),甚至更长时间。

所以,可以看出,limit 中 X 值越大,那么查询速度都越慢。

这个问题呢其实就是 MySQL 中典型的深度分页问题。那问题来了,为什么 limit 越往后查询越慢?如何优化查询速度呢?

为什么limit越来越慢?

在数据库查询中,当使用 LIMIT x, y 分页查询时,如果 x 值越大,查询速度可能会变慢。这主要是因为数据库需要扫描和跳过 x 条记录才能返回 y 条结果。随着 x 的增加,需要扫描和跳过的记录数也增加,从而导致性能下降。

例如 limit 1000000,10 需要扫描 1000010 行数据,然后丢掉前面的 1000000 行记录,所以查询速度就会很慢。

优化手段

对于 MySQL 深度分页比较典型的优化手段有以下两种:

  1. 起始 ID 定位法:使用最后查询的 ID 作为起始查询的 ID。
  2. 索引覆盖+子查询

1.起始ID定位法

起始 ID 定位法指的是 limit 查询时,指定起始 ID。而这个起始 ID 是上一次查询的最后一条 ID。例如上一次查询的最后一条数据的 ID 为 6800000,那我们就从 6800001 开始扫描表,直接跳过前面的 6800000 条数据,这样查询的效率就高了,具体实现 SQL 如下:

select name, age, gender
from person
where id > 6800000 -- 核心实现 SQL
order by id limit 10;

其中 id 字段为表的主键字段。

为什么起始ID查询效率高呢?

因此这种查询是以上一次查询的最后 ID 作为起始 ID 进行查询的,而上次的 ID 已经定位到具体的位置了,所以只需要遍历 B+ 树叶子节点的双向链表(主键索引的底层数据结构)就可以查询到后面的数据了,所以查询效率就比较高,如下图所示:

如果上次查询结果为 9,之后再查询时,只需要从 9 之后再遍历 N 条数据就能查询出结果了,所以效率就很高。

优缺点分析

这种查询方式,只适合一页一页的数据查询,例如手机 APP 中刷新闻时那种瀑布流方式。

但如果用户是跳着分页的,例如查询完第 1 页之后,直接查询第 250 页,那么这种实现方式就不行了。

2.索引覆盖+子查询

此时我们为了查询效率,可以使用索引覆盖加子查询的方式,具体实现如下。

假设,我们未优化前的 SQL 如下:

select name, age, gender
from person
order by createtime desc 
limit 1000000,10;

在以上 SQL 中,createtime 字段创建了索引,但查询效率依然很慢,因为它要取出 100w 完整的数据,并需要读取大量的索引页,和进行频繁的回表查询,所以执行效率会很低。

此时,我们可以做以下优化:

SELECT p1.name, p1.age, p1.gender
FROM person p1
JOIN (
    SELECT id FROM person ORDER BY createtime desc LIMIT 1000000, 10
) AS p2 ON p1.id = p2.id;

相比于优化前的 SQL,优化后的 SQL 将不需要频繁回表查询了,因为子查询中只查询主键 ID,这时可以使用索引覆盖来实现。那么子查询就可以先查询出一小部分主键 ID,再进行查询,这样就可以大大提升查询的效率了。

索引覆盖(Index Coverage)是一种数据库查询优化技术,它指的是在执行查询时,数据库引擎可以直接从索引中获取所有需要的数据,而不需要再回表(访问主键索引或者表中的实际数据行)来获取额外的信息。这种方式可以减少磁盘 I/O 操作,从而提高查询性能。

课后思考

你还知道哪些深度分页的优化手段呢?欢迎评论区留下你的答案。

本文已收录到我的面试小站 www.javacn.site,其中包含的内容有:Redis、JVM、并发、并发、MySQL、Spring、Spring MVC、Spring Boot、Spring Cloud、MyBatis、设计模式、消息队列等模块。

标签:10,面试官,查询,索引,limit,优化,ID
From: https://www.cnblogs.com/vipstone/p/18399160

相关文章

  • 10.面向对象(2)
    MODULE10 面向对象知道继承的好处会使用继承知道继承之后成员变量以及成员方法的访问特点会方法的重写,以及知道方法重写的使用场景会使用this关键字调用当前对象中的成员会使用super关键字调用父类中的成员会定义抽象方法以及抽象类会重写抽象方法一.继承(一)什么是继承1.我......
  • 光影精灵10 Win1+Ubuntu18.04 双系统 踩坑记录
    前言第二年准备报名智能车了,当然还是创意组别。刚好买了今年新出的电脑光影精灵10,我想着也给它安一个双系统。但是没想到,相比于之前那个老电脑,新电脑的新硬件和驱动问题远比老电脑麻烦的多。在经历了一系列踩坑和疯狂查资料之后,加上重装系统N次,终于成功下车。遂把过程记录下来,以......
  • 1000多天我开发了一个免费的跨浏览器的书签同步、阅读排版、任意网页标注插件
    自我介绍大家好,我是阿浩,一位后端开发工程师,同时也略懂前端技术。业余时间,我开发了这款小工具——《藏趣云》。我为什么要写这么个工具需求来源于我自己,因为我是做开发的。我日常都会使用多款浏览器来测试项目,一次需要登录多个账号,寻找各种测试地址链接。之前因为电脑磁盘损坏、......
  • 分享4款安全与认证IC:DS28E30P、MAXQ1065GTC、RNG90-MAVDA-T、RNG90-SSVDA-T(介绍)
    1、DS28E30P安全认证器提供了一种基于FIPS-186ECDSA标准的完整认证解决方案,不仅高度安全,而且易于部署。该安全认证器采用ECDSA挑战和响应认证方式,同时利用安全EEPROM来存储密钥和用户数据。该器件提供了一套核心加密工具,这些加密工具由多种集成块衍生而来,包括一个非对称硬件引擎、......
  • 2024.08.10美团
    1.小美的密码小美准备登录美团,需要输入密码,小美忘记了密码,只记得密码可能是n个字符串中的一个。小美会按照密码的长度从小到大依次尝试每个字符串,对于相同长度的字符串,小美随机尝试,并且相同的密码只会尝试一次。小美想知道,她最少需要尝试多少次才能登录成功,最多需要尝试多少......
  • 【32项目】基于stm32f103c8t6的智能拐杖(文章末尾含完整代码)
    一.设计背景当我们带着家中的老人出去游玩时,难免会遇到有时老人走丢的情况,加上一般他们没有随时携带手机的习惯,很难找到他们,于是我们设计了一款智能的拐杖,通过通过GPS、电子罗盘等模块,来获取经纬度和磁北的夹角,然后通过对方的经纬度计算距离和角度,指向对方的位置,显示为对方的......
  • 解决Windows 10系统更新后谷歌浏览器的兼容性问题
    随着Windows10系统更新的推出,用户可能会遇到谷歌浏览器(Chrome)与更新不兼容的问题,如网页显示错误、扩展程序故障或性能下降等。本教程旨在提供一系列解决方案,帮助用户克服这些问题,确保浏览器平稳运行。(本文由https://chrome.cmrrs.com/站点的作者进行编写,转载时请进行标注。)......
  • 《DNK210使用指南 -CanMV版 V1.0》第二十二章 六轴传感器——原始数据读取实验
    第二十二章六轴传感器——原始数据读取实验1)实验平台:正点原子DNK210开发板2)章节摘自【正点原子】DNK210使用指南-CanMV版V1.03)购买链接:https://detail.tmall.com/item.htm?&id=7828013987504)全套实验源码+手册+视频下载地址:http://www.openedv.com/docs/boards/k210/ATK-......
  • GBJ3510-ASEMI新能源专用整流桥GBJ3510
    编辑:llGBJ3510-ASEMI新能源专用整流桥GBJ3510型号:GBJ3510品牌:ASEMI封装:GBJ-4批号:2024+分类:整流桥特性:整流扁桥、整流桥平均正向整流电流(Id):35A最大反向击穿电压(VRM):1000V恢复时间:>2000ns结温:-55℃~150℃正向峰值电压:1.05V引脚数量:4芯片个数:4芯片尺寸:MILGBJ3510特点芯片与底板电气绝缘......
  • GBJ3510-ASEMI新能源专用整流桥GBJ3510
    编辑:llGBJ3510-ASEMI新能源专用整流桥GBJ3510型号:GBJ3510品牌:ASEMI封装:GBJ-4批号:2024+分类:整流桥特性:整流扁桥、整流桥平均正向整流电流(Id):35A最大反向击穿电压(VRM):1000V恢复时间:>2000ns结温:-55℃~150℃正向峰值电压:1.05V引脚数量:4芯片个数:4芯片尺寸:MILGBJ3510特点......