分库后如何处理分页?

在数据量过大以后,通常都会进行分库操作,把一张表拆分到不同数据库中

例如 tb1 表被拆分到3个库中,分库1、分库2、分库3

现在想执行分页操作

SELECT c1 FROM tb1 ORDER BY c1 LIMIT 4, 2

如何处理呢?查了一些数据库中间件的资料,有一个通用的思路:

到每个分库中取出从0开始、到目标结果集的最后一条记录,汇总到一起,进行排序,然后再取出目标位置的记录集合

例如上面的sql是根据 c1 排序,要取得第5、6两条记录

那么就会对每个分库的 tb1 表执行下面的语句

假设结果分别为

开始按顺序查找

第0条(结果为1)没到第4条,略过

第1条(结果为2)没到第4条,略过

第2条(结果为3)没到第4条,略过

第3条(结果为3)没到第4条,略过

第4条(结果为4)已到第4条,放入结果集

第5条(结果为5)已到第4条,放入结果集

这时结果集合为:4、5,已经达到目标条数2,结束查找

这个思路很简介,实现起来也不复杂,缺点就是当起始位置很大时,所有分库的查询数据将非常大

例如

select c1 from tb1 order by c1 limit 100000000, 2

所有分库都要查询 100000002 条数据,然后再进行汇总排序操作,这个性能很难接受

这个情况也没有特别好的解决办法,但如果各个分库数据分布大致一样,那么可以减少分库大部分结果集

例如sql

select c1 from tb1 order by c1 limit 9999999, 4

现在有3个分库,因为数据分布大致一样,那么可以等分查询

9999999 / 3 = 3333333

各分库执行

假设结果为

找出查询结果中最小和最大值,4、18

以最小值和最大值为界再查询各库,结果为:

查出返回结果中第一条的offset,例如

那么第 3333331 条相当于第 9999996(3333331 + 3333332 + 3333333)条记录,从它开始按顺序查找

略过前3条,取得后面的4条记录,查询完成

原文发布于微信公众号 - 性能与架构(yogoup)

原文发表时间:2016-01-16

本文参与腾讯云自媒体分享计划,欢迎正在阅读的你也加入,一起分享。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏青玉伏案

Swift3.0服务端开发(五) 记事本的开发(iOS端+服务端)

前边以及陆陆续续的介绍了使用Swift3.0开发的服务端应用程序的Perfect框架。本篇博客就做一个阶段性的总结,做一个完整的实例,其实这个实例在《Swift...

2307
来自专栏魏琼东

一步一步教你使用AgileEAS.NET基础类库进行应用开发-基础篇-演示ORM的批量删除与更新

系列回顾           前面的文章一步一步教你使用AgileEAS.NET基础类库进行应用开发-基础篇-演示ORM的基本操作和一步一步教你使用AgileE...

2188
来自专栏玩转JavaEE

elasticsearch API约定(一)

前面我们介绍了一些REST API的基本用法,使读者对API的使用有了一个直观的了解,本文我们来介绍下Elasticsearch中的API约定,这些约定适用于大...

1993
来自专栏三丰SanFeng

无锁编程(五) - RCU(Read-Copy-Update)

RCU(Read-Copy Update) RCU就是指读-拷贝修改,它是基于其原理命名的。对于被RCU保护的共享数据结构,读操作不需要获得任何锁就可以访问,但...

2446
来自专栏鸿的学习笔记

读会搜索引擎

搜索引擎一般由索引管理器,索引检索器,索引构建器,文档管理器组成。 索引管理器,顾名思义是管理带有索引结构的数据,负责对索引的访问。那么索引是怎么管理的呢?不...

1871
来自专栏咸鱼不闲

solr中使用IKAnalyzer配置同义词,停止词,扩展词

第一步 将IKAnalyzer2012FF_u1放到solr-4.7.2/example/solr-webapp/webapp/WEB-INF/lib 目录下 ...

1204
来自专栏Java成神之路

PL/SQL学习笔记_02_游标

        在 PL/SQL 程序中,对于处理多行记录的事务经常使用游标来实现。 

1064
来自专栏天天

Ajax(20171102)

803
来自专栏灯塔大数据

Python-解决Cx_Oracle查询时UnicodeDecodeError的问题

近期在项目中,要对1张100多万条记录的表进行查询,然后进行一些数据的统计,但是在这个过程中,发现只查询出来几条数据就出现了UnicodeDecodeErro...

3146
来自专栏Linux驱动

C-fopen,fwrite,fread,fseek笔记

FILE * fopen(const char * path,const char * mode);

1962

扫码关注云+社区

领取腾讯云代金券