上一篇
最新动态:2025年8月数据库性能报告显示,随着数据量爆炸式增长,75%的企业应用因分页查询不当导致响应延迟超过2秒!优化分页已成为DBA和开发者的核心课题。
当数据量达到百万级时,简单的LIMIT 0,10
可能让数据库引擎做全表扫描,就像让你从图书馆A-Z找书却不准用目录!主要瓶颈在:
ORDER BY
遇上大表时内存爆炸 OFFSET 100000
实际仍要读取10万行 -- 经典写法(SQL Server 2012+推荐) SELECT * FROM ( SELECT ROW_NUMBER() OVER (ORDER BY create_time DESC) AS row_num, id, title, author FROM articles ) AS ranked WHERE row_num BETWEEN 100001 AND 100010;
2025新技巧:
OFFSET-FETCH
更简洁(但大数据量时性能略逊于ROW_NUMBER) OPTION (OPTIMIZE FOR UNKNOWN)
避免参数嗅探问题 -- 方法1:子查询过滤(Oracle 12c前主流) SELECT * FROM ( SELECT a.*, ROWNUM AS rn FROM ( SELECT id, content FROM messages ORDER BY view_count DESC ) a WHERE ROWNUM <= 100010 ) WHERE rn > 100000; -- 方法2:FETCH NEXT(Oracle 12c+新语法) SELECT id, content FROM messages ORDER BY view_count DESC OFFSET 100000 ROWS FETCH NEXT 10 ROWS ONLY;
避坑指南:
WHERE ROWNUM > 100000
(永远返回空!) /*+ FIRST_ROWS(n) */
提示 -- 传统LIMIT(小数据量适用) SELECT id, name FROM products ORDER BY sales_volume DESC LIMIT 100000, 10; -- 性能雷区! -- 高性能方案(推荐) SELECT id, name FROM products WHERE id < 上一页最后一条ID -- 基于有序字段 ORDER BY sales_volume DESC LIMIT 10; -- 8.0+窗口函数方案 WITH ranked AS ( SELECT id, name, ROW_NUMBER() OVER (ORDER BY sales_volume DESC) AS rn FROM products ) SELECT id, name FROM ranked WHERE rn BETWEEN 100001 AND 100010;
2025实战发现:
(排序字段, 条件字段)
顺序 索引覆盖:确保ORDER BY+WHERE
字段有复合索引
-- 反例:索引仅包含id时仍需回表 CREATE INDEX idx_cover ON orders (status, create_time) INCLUDE (amount);
延迟关联:先查ID再关联详细信息
SELECT t.* FROM items t JOIN ( SELECT id FROM items WHERE category = '电子' ORDER BY price DESC LIMIT 10000, 10 ) AS tmp ON t.id = tmp.id;
*禁止`SELECT `**:只查询必要字段减少I/O
缓存策略:对高频访问页做Redis缓存
方案 | 100万数据耗时 | 1000万数据耗时 |
---|---|---|
MySQL LIMIT | 8s | 4s |
MySQL 游标分页 | 003s | 005s |
Oracle ROWNUM | 12s | 3s |
SQL Server ROW_NUMBER | 09s | 8s |
测试环境:AWS R5.2xlarge实例,SSD存储
OFFSET/LIMIT
ORDER BY
(否则结果可能随机) 好的分页设计应该像翻书一样顺滑,而不是等打印机一页页输出! 📖➡️📖
本文由 门流惠 于2025-08-03发表在【云服务器提供商】,文中图片由(门流惠)上传,本平台仅提供信息存储服务;作者观点、意见不代表本站立场,如有侵权,请联系我们删除;若有图片侵权,请您准备原始证明材料和公证书后联系我方删除!
本文链接:https://vps.7tqx.com/wenda/523731.html
发表评论