PageHelpher、MyBatis关联查询,多表查询分页问题


一般MyBatis作为ORM框架,需要做分页一般会选择使用PageHelper。PageHelper非常强大的分页插件,和mybatis整合也非常方便。PageHelper对单表分页或者整体结果集分页是比较方便的。


不过有时我们会遇到这样的问题。利用MyBatis做多表的关联查询,分页的对象不是所有结果集,而是对其中一张表分页,然后再关联其他表的数据,如果直接使用PageHelper进行分页的话,分页结果可能会不正确。


举个例子:

SELECT d.*,c.* FROM channel_data d LEFT JOIN channel_comment c 
    ON d.id = c.dataId  ORDER BY d.pubtime DESC,c.pubtime ASC LIMIT 0,15

比如 channel_data里面有5条数据。channel_comment里面的数据与channel_data有关联,channel_data与channel_comment是一对多的关系。也就是说一个channel_data对象里面可能包含了多条channel_comment。也就是channel_data对象里面有一个List存放channel_comment。那么查询的时候自然是要对channel_data进行分页。但如果直接用PageHelpher分页,产生的SQL就如上面所示。通过left join 查询出的数据不止5条。那么PageHelper的分页机制得出的结果就不是我们想要的。


怎么解决这个问题呢?有些网友提出,如果PageHelper能解析sql注释的方法就好了。

据了解,在sql添加/**/这种注释是SQL的标准语法,在mapper中定义的sql中添加这种注释,mybatis也会把注释透传给数据库,如此一来,就可以用注释来作文章,比如:


select * from (/*start*/select * from a/*end*/) ta left join b tb on tb.ref_id = ta.id


pagehelper是有解析sql的步骤的,那么可以通过解析“start”“end”这种注释标签,来知晓添加分页、排序的位置。那么不就可以指定分页的位置了吗?想法是好的,但显然PageHelper目前不具备这个能力。


所以我们只能手动构造分页SQL而不能直接用PageHelper。额,好像到头来什么都没有说。

但一般遇到这种情况,我们会先把需要分页的数据分页。得到其结果集后再进行关联查询。这样就可以得到想要的结果。


比如上面的SQL就变为:


    SELECT d.*,c.* FROM (SELECT * FROM channel_data  LIMIT 0,15) d LEFT JOIN channel_comment c 
    ON d.id = c.dataId  ORDER BY d.pubtime DESC,c.pubtime ASC

这样查询就能得到想要的结果集了,只不过需要自己手动统计count。






你可能感兴趣的:(其他)