php查询数据怎么分页查_limit分页公式及用法【详解】
发布时间 - 2026-01-02 00:00:00 点击率:次LIMIT offset, length 是最常用写法,但 offset 偏移量大时性能骤降,且排序字段不唯一会导致漏行或重复;应优先考虑游标分页,并严格校验分页参数。
MySQL 的 LIMIT 分页语法怎么写才不跳数据
直接说结论:LIMIT offset, length 是最常用写法,但 offset 偏移量变大时性能会明显下降,且在有重复排序字段(比如时间相同)时容易漏行或重复。不是所有分页都适合用它。
典型错误是这样写:SELECT * FROM user ORDER BY id LIMIT 10000, 20 —— 当 offset 超过几万,MySQL 要先扫描前 10020 行再丢弃前 10000 行,IO 和 CPU 开销陡增。
-
offset为 0 时最快,越往后越慢 - 如果
ORDER BY字段不唯一(如多个记录created_at相同),LIMIT无法保证稳定顺序,翻页可能看到重复或丢失数据 - PHP 中拼接 SQL 时,务必对
$page和$pageSize做整型校验,否则易被注入或报错
PHP 中计算 offset 的安全公式
分页本质是算出从第几条开始取,公式就是:offset = ($page - 1) * $pageSize。注意:页码必须从 1 开始,不能从 0;$page 必须是正整数,$pageSize 通常限制在 1–100 之间。
常见疏漏:
立即学习“PHP免费学习笔记(深入)”;
- 没做
max(1, (int)$page)校验,传入负数或字符串导致offset为 0 或负值,MySQL 报错Invalid argument - 没限制
$pageSize上限,攻击者传?limit=1000000可能拖垮数据库 - 没统一处理空参,默认值设在 SQL 层(如
IFNULL)不如在 PHP 层早拦住
php $page = max(1, (int)($_GET['page'] ?? 1)); $pageSize = max(1, min(100, (int)($_GET['limit'] ?? 20))); $offset = ($page - 1) * $pageSize;$stmt = $pdo->prepare("SELECT id, name FROM user ORDER BY id ASC LIMIT :offset, :length"); $stmt->bindValue(':offset', $offset, PDO::PARAM_INT); $stmt->bindValue(':length', $pageSize, PDO::PARAM_INT); $stmt->execute();
什么时候该换 Cursor 分页代替 LIMIT
当列表需按时间倒序、且数据高频写入(如消息流、日志),用 LIMIT offset, length 会越来越卡,还可能因新插入数据导致“上一页末尾”和“下一页开头”之间出现断层或重复。这时应改用基于游标的分页(Cursor-based Pagination)。
核心思路:不依赖行号,而用上一页最后一条的排序字段值作为下一页起点。
- 要求排序字段(如
id或created_at)必须有索引,且尽量唯一 - 首次请求不带
cursor,后续请求传上一页最后一条的id(比如?cursor=12345) - SQL 改为:
WHERE id ,避免OFFSET - PHP 中需确保
cursor是合法整型,且大于 0,否则拒绝查询
php
$cursor = (int)($_GET['cursor'] ?? 0);
if ($cursor > 0) {
$stmt = $pdo->prepare("SELECT id, title FROM article WHERE id < ? ORDER BY id DESC LIMIT 20");
$stmt->execute([$cursor]);
} else {
$stmt = $pdo->prepare("SELECT id, title FROM article ORDER BY id DESC LIMIT 20");
$stmt->execute();
}
count(*) 分页总数要不要查
查总数(SELECT COUNT(*))看起来直观,但对大表是性能杀手。尤其当只展示「下一页」按钮、不
显示总页数时,完全没必要查。
更务实的做法:
- 只查一页数据(比如 20 条),然后判断是否查到了满额(20 条)。如果不到 20 条,说明已是最后一页
- 需要总数时,用近似值:
SHOW TABLE STATUS LIKE 'user'查Rows字段(MyISAM 准确,InnoDB 是估算) - 或者加缓存:总数变化不频繁时,用 Redis 缓存
user:count,定时或写操作后更新 - 绝对避免在分页接口里每次执行
SELECT COUNT(*) FROM ... WHERE ... ORDER BY ...,WHERE 条件复杂时可能比主查询还慢
游标分页天然不依赖总数,所以也绕开了这个问题。
# mysql
# php
# redis
# red
# sql
# count
# select
# 整型
# 字符串
# int
# 接口
# Length
# table
# 数据库
# 分页
# 下一页
# 上一页
# 行号
# 报错
# 最常用
# 不依赖
# 首次
# 多个
相关栏目:
【
网站优化151355 】
【
网络推广146373 】
【
网络技术251813 】
【
AI营销90571 】
相关推荐:
Windows10怎样连接蓝牙设备_Windows10蓝牙连接步骤【教程】
清除minerd进程的简单方法
教你用AI将一段旋律扩展成一首完整的曲子
高端建站三要素:定制模板、企业官网与响应式设计优化
英语简历制作免费网站推荐,如何将简历翻译成英文?
如何快速生成专业多端适配建站电话?
如何在腾讯云服务器上快速搭建个人网站?
Laravel Facade的原理是什么_深入理解Laravel门面及其工作机制
高端云建站费用究竟需要多少预算?
武汉网站设计制作公司,武汉有哪些比较大的同城网站或论坛,就是里面都是武汉人的?
制作无缝贴图网站有哪些,3dmax无缝贴图怎么调?
宙斯浏览器怎么屏蔽图片浏览 节省手机流量使用设置方法
如何在服务器上配置二级域名建站?
Windows Hello人脸识别突然无法使用
Laravel怎么解决跨域问题_Laravel配置CORS跨域访问
HTML5建模怎么导出为FBX格式_FBX格式兼容性及导出步骤【指南】
常州企业网站制作公司,全国继续教育网怎么登录?
Laravel Session怎么存储_Laravel Session驱动配置详解
php中::能调用final静态方法吗_final修饰静态方法调用规则【解答】
Laravel如何使用模型观察者?(Observer代码示例)
UC浏览器如何切换小说阅读源_UC浏览器阅读源切换【方法】
网站设计制作书签怎么做,怎样将网页添加到书签/主页书签/桌面?
WordPress 子目录安装中正确处理脚本路径的完整指南
如何用PHP快速搭建高效网站?分步指南
美食网站链接制作教程视频,哪个教做美食的网站比较专业点?
黑客如何利用漏洞与弱口令入侵网站服务器?
如何快速选择适合个人网站的云服务器配置?
小视频制作网站有哪些,有什么看国内小视频的网站,求推荐?
linux写shell需要注意的问题(必看)
大同网页,大同瑞慈医院官网?
打开php文件提示内存不足_怎么调整php内存限制【解决方案】
Laravel PHP版本要求一览_Laravel各版本环境要求对照
使用豆包 AI 辅助进行简单网页 HTML 结构设计
怎么制作一个起泡网,水泡粪全漏粪育肥舍冬季氨气超过25ppm,可以有哪些措施降低舍内氨气水平?
Laravel怎么连接多个数据库_Laravel多数据库连接配置
ChatGPT 4.0官网入口地址 ChatGPT在线体验官网
Laravel如何实现数据库事务?(DB Facade示例)
Laravel如何发送系统通知?(Notification渠道示例)
高端智能建站公司优选:品牌定制与SEO优化一站式服务
如何在建站宝盒中设置产品搜索功能?
Laravel如何设置自定义的日志文件名_Laravel根据日期或用户ID生成动态日志【技巧】
如何用虚拟主机快速搭建网站?详细步骤解析
Laravel如何与Pusher实现实时通信?(WebSocket示例)
QQ浏览器网页版登录入口 个人中心在线进入
Laravel如何使用Service Provider服务提供者_Laravel依赖注入与容器绑定【深度】
Laravel队列任务超时怎么办_Laravel Queue Timeout设置详解
手机钓鱼网站怎么制作视频,怎样拦截钓鱼网站。怎么办?
深圳防火门网站制作公司,深圳中天明防火门怎么编码?
Linux系统命令中screen命令详解
Laravel如何实现多对多模型关联?(Eloquent教程)

