关于分页的一次失败的尝试
来源:互联网 发布:全局搜索能力强的算法 编辑:程序博客网 时间:2024/05/21 10:21
工作2年,几个项目下来对现有的东西做改进似乎是顺其自然的事情。
分页查询差不多是每个项目都要用的东西,比较通用的实现方法是:直接在数据库分页,针对不同数据库,分页方式也是有所差别的。一般来说代码是这样的:(我用mysql)
/** * 查询分页信息 * @param pageInfo 分页对象中包含的对象的类信息。 * @param sql 数据库查询语句 * @param pageStart 第几页 * @param pageSize 每页多少条记录 * @param args 查询条件 * @return 分页好的分页信息 */public <T> Page<T> paginate(Class<T> pageInfo,String sql, int pageStart, int pageSize,String sort,String sortD,Object... args) {StringBuilder pageSql=new StringBuilder(128);pageSql.append(sql).append(" LIMIT ").append(pageStart).append(",").append(pageSize);if(sort!=null&&sortD!=null){//拼接排序方式pageSql.append(" order by ").append(sort).append(" ").append(sortD);}String pageCount="select count(1) "+sql.substring(sql.indexOf("from "));//替换掉from 之前的部分为select count(1)Integer total=queryObject(pageCount, Integer.class, args);//用springTemple实现的数据库查询,执行sql,查询记录总数List<T> data= queryObjectList(pageSql.toString(), pageInfo, args);//执行sql,查询出一页的数据到集合Page<T> page=new Page<T>(data, total);return page;}
这方法也算经典吧,但若是对于同一个分页查询,只是做页面间的跳转的话获取 记录总数 的查询是不是在做重复劳动呢?为此我的一个思路是对查询语句,查询条件做hash,提取其信息摘要,以摘要为键将记录总是保存在缓存中,这个缓存最好和会话有关系,如果会话结束缓存可以得到释放。我的代码是下面这个样子:
public <T> Page<T> paginate(Class<T> pageInfo,String sql, int pageStart, int pageSize,String sort,String sortD,Object... args) {/*这种尝试是徒劳的,如果在其他地方为对应的表增加或删除了记录,这里是无法感知的,故记录总数就会停留在第一次查询且查询条件没变的样子*/String pageHash;if(args==null){//获取摘要pageHash=FrameUtils.encryptMD5(sql);}else{pageHash=FrameUtils.encryptMD5(sql, Arrays.asList(args).toString());}StringBuilder pageSql=new StringBuilder(128);pageSql.append(sql).append(" LIMIT ").append(pageStart).append(",").append(pageSize);if(sort!=null&&sortD!=null){//拼接排序方式pageSql.append(" order by ").append(sort).append(" ").append(sortD);}String pageCount="select count(1) "+sql.substring(sql.indexOf("from "));//替换掉select 与 from 之间的部分为 count(1)/*获取当前用户的会话,我用的shiro做安全框架,所以就在这里侵入一下了,有点不通用*/Session session=SecurityUtils.getSubject().getSession();Integer total;if(session.getAttribute(pageHash)!=null){/*如果找到,则不进行数据库查询*/total=(Integer)session.getAttribute(pageHash);}else{/*如果没有找到对应的值,则重新查询*/total=queryObject(pageCount, Integer.class, args);session.setAttribute(pageHash, total);}Integer total=queryObject(pageCount, Integer.class, args);List<T> data= queryObjectList(pageSql.toString(), pageInfo, args);Page<T> page=new Page<T>(data, total);return page;}
当我要实现新增删除的时候,才发现这是多么幼稚的想法,被分页的数据发生变动后,数据总数就会跟实际数据不符。若是翻到最后一页就会暴露问题所在。
作为一个通用的分页方式,这是不可取的。
但这个方法在特殊环境下也是有用的。比如在只做查询地方,数据总数在查询的时候不发生变化就没问题。还有就是在数据量很大,且对数据分页总的显示与实际数据的匹配情况出现差异可以容忍的环境,这个都是不错的方式。
但总的来说,我是想弄个通用的分页的新方法的,结果还是失败了,但也长进了不少。
- 关于分页的一次失败的尝试
- DexClassLoader一次失败的尝试
- 关于稳定物理关节的一次尝试
- Win7下尝试编译Fast RCNN---- 一次失败的经历
- 一起来写ftp server 02 -- 一次失败的尝试
- 手机模块化梦想:Google的一次失败尝试
- 关于Sqlserver2012分页的新功能尝试
- 一次无聊的尝试...
- 失败的尝试
- 失败的尝试
- 一次关于分页语句的改写优化
- 一次有益的敏捷尝试
- 一次小小的模板尝试
- 极路由的一次尝试
- zabbix 的一次优化尝试
- 记一次失败的尝试--ubuntu下把笔记本无线网卡的驱动替换掉
- 一次失败的QThread多线程加载Webpage.load()页面的尝试
- 记一次FFMPEG转avi视频保存到ftp服务器的失败尝试
- SharePoint Excel Service-PowerShell
- ExcelXML
- 数学之美系列六:图论和网络爬虫 (Web Crawlers)
- LeetCode-Palindrome Number
- libavformat
- 关于分页的一次失败的尝试
- 在XML中定义逐帧动画
- UVa 10916 - Factstone Benchmark
- jquery Temp jsonToAction
- Android心得体会 -- Activity改写成类似Dialog实现弹出式菜单
- 如何在zencart里实现多标签标签云效果
- 1366 Incorrect integer value
- 相机防抖
- ubuntu 安装nginx