SQL 实战:分页查询的多种方式对比与优化

在处理大数据表时,分页查询是非常常见的需求。分页不仅可以提高用户体验,还能有效减少数据库查询返回的数据量,避免一次性加载大量记录引起的性能瓶颈。
然而,在数据量较大或复杂查询中,简单的分页方式可能导致性能下降。本文将探讨 SQL 中实现分页查询的不同方式,并对比它们的优缺点,帮助优化大数据量场景下的分页方案。


一、分页查询的常见方式

1. 基本分页方式:LIMIT OFFSET
  • 语法
SELECT * FROM orders  
ORDER BY order_date DESC  
LIMIT 10 OFFSET 20;  -- 跳过前 20 条,返回第 21~30 条
  • 说明LIMIT 指定返回的行数,OFFSET 指定跳过的行数。

2. 使用 ROW_NUMBER() 进行分页
  • 适用数据库:MySQL 8.0 及以上、SQL Server、PostgreSQL
  • 语法
WITH ordered_orders AS (  SELECT order_id, order_date,  ROW_NUMBER() OVER (ORDER BY order_date DESC) AS rn  FROM orders  
)  
SELECT *  
FROM ordered_orders  
WHERE rn BETWEEN 21 AND 30;
  • 说明
    • ROW_NUMBER() 为每一行分配唯一编号,可通过 WHERE 进行分页筛选。
    • 分页不受数据量影响,性能稳定。

3. 游标分页(基于主键或唯一索引)
  • 适用场景:持续查询下一页数据,适合前端“加载更多”方式。
  • 语法
SELECT * FROM orders  
WHERE order_date < '2024-01-01 00:00:00'  
ORDER BY order_date DESC  
LIMIT 10;
  • 说明
    • 基于主键或时间字段进行分页,避免大偏移量问题,性能更优。
    • 适合按时间或 ID 递增的分页加载,避免全表扫描。

4. 使用 SQL_CALC_FOUND_ROWS 计算总数
  • 语法
SELECT SQL_CALC_FOUND_ROWS * FROM orders  
LIMIT 10 OFFSET 20;  
SELECT FOUND_ROWS();
  • 说明
    • 查询结果同时计算总行数,减少一次额外的 COUNT(*) 查询。
    • 在 MySQL 8.0 以后不推荐,效率较低。


二、实战案例:大数据分页方案设计与优化


案例 1:简单分页(LIMIT OFFSET

需求描述
查询订单表中按下单日期排序的第 1001-1020 条订单记录。


SQL 实现

SELECT order_id, customer_id, order_date  
FROM orders  
ORDER BY order_date DESC  
LIMIT 20 OFFSET 1000;

优点

  • 简单直接,适合小数据量分页。

缺点

  • OFFSET 较大时(如 100000),性能下降显著。
  • 数据量越大,查询速度越慢,因为数据库仍需扫描前 OFFSET 行。


案例 2:使用 ROW_NUMBER() 实现分页

需求描述
查询订单表中,按订单金额降序排列的第 51-60 条记录。


SQL 实现

WITH cte_orders AS (  SELECT order_id, amount,  ROW_NUMBER() OVER (ORDER BY amount DESC) AS rn  FROM orders  
)  
SELECT * FROM cte_orders  
WHERE rn BETWEEN 51 AND 60;

优点

  • 即使数据量大,ROW_NUMBER() 也能有效避免大偏移量问题。
  • 使用 CTE(公用表表达式),代码更清晰。

缺点

  • 需要 SQL 8.0 以上版本或其他支持窗口函数的数据库。


案例 3:游标方式分页(基于索引分页)

需求描述
查询比上次加载时间更早的订单记录,每次加载 20 条记录。


SQL 实现

SELECT order_id, customer_id, order_date  
FROM orders  
WHERE order_date < '2024-05-01 00:00:00'  
ORDER BY order_date DESC  
LIMIT 20;

优点

  • 不依赖 OFFSET,即使数据量大也能快速查询。
  • 可动态加载下一页,避免重复数据查询。

缺点

  • 需要前端记录上一页最后一条数据的时间或 ID。


案例 4:SQL_CALC_FOUND_ROWS 计算总记录数

需求描述
查询订单表第 21-40 条记录,同时返回总记录数,用于前端分页展示。


SQL 实现

SELECT SQL_CALC_FOUND_ROWS order_id, customer_id  
FROM orders  
ORDER BY order_date DESC  
LIMIT 20 OFFSET 20;  SELECT FOUND_ROWS();

优点

  • 无需额外执行 COUNT(*) 查询,减少一次数据库交互。

缺点

  • MySQL 8.0 开始弃用,SQL_CALC_FOUND_ROWS 效率较低。


三、性能对比与优化策略


1. 性能对比
方式性能表现(小数据)性能表现(大数据)复杂性推荐场景
LIMIT OFFSET简单小数据量、简单分页
ROW_NUMBER()一般大数据量分页、多层次筛选
游标分页较复杂无限加载、动态分页
SQL_CALC_FOUND_ROWS简单需要总行数时(不推荐大数据量)


2. 大数据分页优化策略
  1. 避免深度分页
  • 限制最大 OFFSET,提供“跳页”或“前端加载更多”方式。
  • 使用游标或基于索引的分页方式逐步加载数据。
  1. 索引优化
  • 在分页查询涉及的字段上建立索引,提高数据检索效率。
CREATE INDEX idx_order_date ON orders(order_date);
  1. 改用 ROW_NUMBER()
  • 对于复杂多条件查询,使用窗口函数(如 ROW_NUMBER())替代 LIMIT OFFSET,能有效避免性能下降问题。
  1. 提前过滤数据
  • 分页前尽可能过滤不必要的数据,减少扫描行数。
SELECT * FROM orders  
WHERE status = 'completed'  
ORDER BY order_date DESC  
LIMIT 20 OFFSET 2000;


四、总结

  • 小数据量分页:使用 LIMIT OFFSET 简单高效。
  • 大数据量分页:优先选择游标或基于索引的分页方式,减少 OFFSET 扫描行数。
  • 复杂分页:使用 ROW_NUMBER() 结合 CTE 实现多层次分页,性能稳定,推荐大数据环境下使用。
  • 动态加载:基于唯一索引或时间字段的游标分页方式,在实际业务中更具实用性,避免性能瓶颈。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/500432.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

linux装git

前言 以 deepin 深度系统为例&#xff0c;安装命 令行版 Git 非常简单。 安装 注意&#xff1a;需要输入账号密码&#xff0c;否则无法进行。 打开终端&#xff0c;执行如下命令即可。 sudo apt-get install git成功 如下图所示&#xff0c;输入 git &#xff0c;命令识别即…

【Spark】架构与核心组件:大数据时代的必备技能(下)

&#x1f407;明明跟你说过&#xff1a;个人主页 &#x1f3c5;个人专栏&#xff1a;《大数据前沿&#xff1a;技术与应用并进》&#x1f3c5; &#x1f516;行路有良友&#xff0c;便是天堂&#x1f516; 目录 一、引言 1、什么是Apache Spark 2、Spark 的应用场景&…

NLP中的神经网络基础

一&#xff1a;多层感知器模型 1&#xff1a;感知器 解释一下&#xff0c;为什么写成 wxb>0 &#xff0c;其实原本是 wx > t ,t就是阈值&#xff0c;超过这个阈值fx就为1&#xff0c;现在把t放在左边。 在感知器里面涉及到两个问题&#xff1a; 第一个&#xff0c;特征提…

第十一章 图论

题目描述&#xff1a; 阿里这学期修了计算机组织和架构课程。他了解到指令之间可能存在依赖关系&#xff0c;比如WAR&#xff08;读后写&#xff09;、WAW、RAW。 如果两个指令之间的距离小于安全距离&#xff0c;则会导致危险&#xff0c;从而可能导致错误的结果。因此&#…

嵌入式系统 第七讲 ARM-Linux内核

• 7.1 ARM-Linux内核简介 • 内核&#xff1a;是一个操作系统的核心。是基于硬件的第一层软件扩充&#xff0c; 提供操作系统的最基本的功能&#xff0c;是操作系统工作的基础&#xff0c;它负责管理系统的进程、内存、设备驱动程序、文件和网络系统&#xff0c; 决定着系统的…

win11蓝屏死机 TPM-WMI

1. 打开win11的事件查看器&#xff0c;定位错误 最近两次都是 KB5016061&#xff1a;安全启动数据库和 DBX 变量更新事件 - Microsoft 支持 事件源 TPM-WMI 事件 ID 1796 2. 解决方案 打开注册表&#xff1a;计算机\HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Contro…

Linux命令——3.网络与用户

文章目录 一、网络1.网络测试与诊断2.网络接口配置3.无线网络配置4.防火墙与网络管理6.防火墙管理1&#xff09;firewalld命令2&#xff09;iptables命令 二、用户和群组1.管理员模式2.用户账户管理1&#xff09;useradd创建2&#xff09;usermod修改3&#xff09;userdel 删除…

机器学习算法基础知识1:决策树

机器学习算法基础知识1&#xff1a;决策树 一、本文内容与前置知识点1. 本文内容2. 前置知识点 二、场景描述三、决策树的训练1. 决策树训练方式&#xff08;1&#xff09;分类原则-Gini&#xff08;2&#xff09;分类原则-entropy&#xff08;3&#xff09;加权系数-样本量&am…

_使用CLion的Vcpkg安装SDL2,添加至CMakelists时报错,编译报错

语言&#xff1a;C20 编译器&#xff1a;gcc 14.2 摘要&#xff1a;初次使用Vcpkg添加SDL2&#xff0c;出现CMakelists找不到错误、编译缺失main错误、运行失败错误。 CMakelists缺失错误&#xff1a; 使用CLion的Vcpkg安装SDL2时&#xff0c;按照指示把对应代码添加至CMakel…

Lumos学习王佩丰Excel第二十二讲:制作甘特图与动态甘特图

一、制作双向条形图 1. 分离坐标轴 2. 自定义坐标轴数字格式&#xff1a;加分号加正常数字 3. 修改图表背景 修改图片艺术效果&#xff1a;虚化图片 二、制作甘特图 1、甘特图定义 甘特图&#xff08;Gantt chart&#xff09;又称为横道图、条状图&#xff08;Bar chart&…

el-pagination 为什么只能展示 10 条数据(element-ui@2.15.13)

好的&#xff0c;我来帮你分析前端为什么只能展示 10 条数据&#xff0c;以及如何解决这个问题。 问题分析&#xff1a; pageSize 的值&#xff1a; 你的 el-pagination 组件中&#xff0c;pageSize 的值被设置为 10&#xff1a;<el-pagination:current-page"current…

【网络安全实验室】SQL注入实战详情

如果额头终将刻上皱纹&#xff0c;你只能做到&#xff0c;不让皱纹刻在你的心上 1.最简单的SQL注入 查看源代码&#xff0c;登录名为admin 最简单的SQL注入&#xff0c;登录名写入一个常规的注入语句&#xff1a; 密码随便填&#xff0c;验证码填正确的&#xff0c;点击登录…

ruoyi 多租户 开启后针对某一条sql不适用多租户; 若依多租户sql规则修改

文章参考&#xff1a;多租户功能 | Ruoyi-TDesign 忽略租户​ 1.如果需要指定单独 SQL 不开启过滤&#xff0c;可在对应的 Mapper 接口添加如下忽略注解&#xff1a; InterceptorIgnore(tenantLine "true", dataPermission "false") 此处注意事项 使…

一文理解条件竞争漏洞

视频教程在我主页简介或专栏里 目录&#xff1a; 理解竞争条件的基本概念 限制超越型竞争条件 使用 Burp Repeater 检测和利用限制超限竞态条件 方法论 1 — 预测潜在的冲突 2 — 线索 3 — 概念验证 如何防止竞态条件漏洞 理解竞争条件的基本概念 竞争条件(也就是条件竞…

一种基于动态部分重构的FPGA自修复控制器

1.FPGA动态部分重构技术 动态部分重构技术指在FPGA运行时&#xff0c;通过加载部分位流文件来修改FPGA可重构区域中的逻辑设计&#xff0c;修改过程中其余逻辑功能不受影响整个系统也能够持续运行。 下图为FPGA动态部分重构的基本原理图。通过下载A1.bit、A2.bit、A3.bit 或A4.…

计算机网络体系结构基础知识

一、计算机网络的两个目标&#xff1a; ①两台计算机之间通信 ②两台计算机之间的资源共享 二、计算机网络概述 1.定义&#xff1a;利用通信线路将地理上分散的、具有独立功能的计算机系统和通信设备按不同 的形式连接起来&#xff0c;以功能完善的网络软件及协…

云计算学习架构篇之HTTP协议、Nginx常用模块与Nginx服务实战

一.HTTP协议讲解 1.1rsync服务重构 bash 部署服务端: 1.安装服务 [rootbackup ~]# yum -y install rsync 2.配置服务 [rootbackup ~]# vim /etc/rsyncd.conf uid rsync gid rsync port 873 fake super yes use chroot no max connections 200 timeout 600 ignore erro…

合合信息亮相CSIG AI可信论坛,全面拆解AI视觉内容安全的“终极防线”

合合信息亮相CSIG AI可信论坛&#xff0c;全面拆解视觉内容安全的“终极防线”&#xff01; &#x1f42f; AI伪造泛滥&#xff0c;我们还能相信“眼见为实”吗&#xff1f; 近期&#xff0c;由中国图象图形学学会主办的CSIG青年科学家会议 AI可信论坛在杭州成功举办。本次论…

AI 智能助手对话系统

一个基于 React 和 Tailwind CSS 构建的现代化 AI 对话系统&#xff0c;提供流畅的用户体验和丰富的交互功能。 项目链接&#xff1a;即将开放… 功能特点 &#x1f916; 智能对话&#xff1a;支持与 AI 助手实时对话&#xff0c;流式输出回答&#x1f4c1; 文件处理&#xff…

经验证:将数据从索尼传输到Android的 4 种方法

概括 像Android Galaxy S20 这样的新型Android智能手机很酷&#xff0c;但除了将数据从索尼传输到Android之外。众所周知&#xff0c;旧的索尼手机上存储着大量的文件&#xff0c;因此将数据从旧的索尼手机传输到新的Android手机非常重要。为了解决这个问题&#xff0c;我们做…