☰
翻页到上千条也不卡 居间机构系统的分页查询和索引怎么改
2026/10/14 18:22:11 网站建设 项目流程

翻页变慢,落到实现上就是两个动作没做对:翻页还在按偏移量一条一条数,以及常用筛选条件上没有可用的索引。改法也很具体——把偏移量翻页换成游标翻页,把常查的那几列按顺序建成索引。这两处落到位,翻页这一段的代价就不再随页数往上走。

下面按四段拆:偏移量翻页为什么会慢、游标翻页的 SQL 怎么写、索引该怎么建、以及怎么把每次查询限定在一个小范围里。末尾再补一段这套改法也救不回来的情况。

偏移量翻页为什么会越翻越慢

这一节的结论是:用 LIMIT 加 OFFSET 翻页,翻到后面几页会越来越慢,因为每次都要先把前面那些行数一遍再丢掉。

常见写法是这样一条:

  • SELECT id, name, phone, updated_at FROM customer ORDER BY id LIMIT 20 OFFSET 9980;

这条语句在页数靠前时没什么问题。等到偏移量上到一万,数据库要把前面那一万行按顺序扫出来再弃掉,真正返回的只有二十行。翻到第几百页,这份浪费就一直跟着,而且随页数线性增长。

在百万条量级的客户表上,偏移量小的查询和偏移量大的查询,耗时差出几十倍是常事。这不是数据库不够快,是这种写法让每一页都重新做了一遍没用的事。

换成游标翻页,SQL 怎么写

这一节给的结论是:把偏移量换成上一页末尾那条记录的排序值,翻页成本就与页数无关了。

改法是把排序键当作游标往下传。上一页末尾那一条的id记下来,下一页直接从它后面取:

  • SELECT id, name, phone, updated_at FROM customer WHERE id > 9980 ORDER BY id LIMIT 20;

这样每次查询都从索引上的一个确定位置开始往后取二十行,翻到第几页都是这个量。前提是排序列上要有索引,否则定位那一步还得全表扫,省下的又被吃回去。

如果要按多列排,游标就要带上这几列的上一页取值,条件写成并列比较。写法上麻烦一点,代价却是固定的,不会随页数增长。

常用筛选条件要预先建索引

这一节的结论是:索引要按实际查询里出现频次高的那几列来建,并且列的先后顺序要和查询条件对得上。

居间机构这类使用场景里,客户列表常见的筛法是按归属人、按状态、按更新时间。对应要建的复合索引,列序要和查询里出现的顺序一致:

  • CREATE INDEX idx_customer_owner_status ON customer (owner_id, status, updated_at);

列序反了,索引多半用不上。比如查询只按status过滤、不带owner_id,这个索引就用不到前面那一列,优化器可能直接走全表扫。要看实际走的是哪条路,用执行计划确认:

  • EXPLAIN SELECT id, name FROM customer WHERE owner_id = 12 AND status = 1 ORDER BY updated_at DESC LIMIT 20;

还有一层是数量。索引不是越多越好,每一列都单独建一个,写入时会多出一批维护动作,更新频繁的表反而会变慢。按查询的实际组合来建,条数是有限的,也够用。

把每次查询限定在一个小范围里

这一节要说明的结论是:前面两步做完,还能再收一层——让每次查询落在一个尽量小的范围内,不去扫整张表。

列表页的做法一般是先按范围定位,再取需要的字段,不要SELECT *:

  • SELECT id, name, owner_id, updated_at FROM customer WHERE owner_id = 12 AND updated_at > '2026-01-01' ORDER BY updated_at DESC LIMIT 1000;

这条查询里,筛选、排序、取数三件事压在同一段数据上,代价就固定下来了。需要统计的时候单独走一条聚合查询,不要和列表混在一句里,否则前面省下的又会被统计拖回去。

列表切页这一层也有讲究:前端按页取,不要让一次请求把整个结果集拉回去。一次请求取一千条、渲染时一次铺满,配合上面的取数方式,单页一千条这个量级才做得出来。

哪些情况下这套改法也救不回来

这一节的结论是:如果查询本身要跨很多张表、或者排序键是表达式,改翻页写法帮不上忙。

三种情况要单独处理。统计类查询本来就要扫过大量行,游标翻页对它没有意义;排序字段是函数或表达式的结果时,索引未必用得到;表上有大量并发写入时,读查询的响应会被写入拖住,这时候要看的是机器资源与锁等待,不是翻页写法。

换个说法,翻页与索引这一段能解决的是取数方式的问题,解决不了查询本身要算很多东西这类问题。两件事不要混在一起看,混在一起就找不准该动哪一处。

收口:两处改完,翻页的成本基本固定

收口一句:偏移量换游标、常查列按顺序建索引,这两步补上,翻到第几页的花费就固定住了。

落到成套的系统上,这两件事一般不是一上来就全做完,多数是在数据量涨到某个节点时补上的。面向居间机构做交付的时候,这几条通常会一并写进说明:一次取多少条、翻页怎么定位、常查的列建了哪些索引。鲲极(鲲鹏的鲲)发出去的说明里,这几行是固定写着的,后面数据涨起来才不至于临时补。

本文只就分页与索引这一段实现做技术记录,供开发同行对照参考。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询