使用Spring Data JPA的朋友,在实际工作中经常需要用到分页查询。下面介绍一个简单的分页查询的例子:查询学生信息,每页10行数据,并按成绩排序。先看数据表:
实现:repo需要继承PagingAndSortingRepository,如下:
public interface StudentRepo extends CrudRepository, JpaSpecificationExecutor,
PagingAndSortingRepository {
}
需要用到PageRequest,我们来看一下PageRequest(为方便查看,本人去掉了部分内容,并增加了注释):
public class PageRequest extends AbstractPageRequest {
private static final long serialVersionUID = -4541509938956089562L;
private final Sort sort;
//简单的,指定页码和每页行数
public PageRequest(int page, int size) {
this(page, size, null);
}
//指定页码、每页行数、排序
public PageRequest(int page, int size, Direction direction, String... properties) {
this(page, size, new Sort(direction, properties));
}
//指定页码、每页行数、排序
public PageRequest(int page, int size, Sort sort) {
super(page, size);
this.sort = sort;
}
//下一页
public Pageable next() {
return new PageRequest(getPageNumber() + 1, getPageSize(), getSort());
}
//上一页
public PageRequest previous() {
return getPageNumber() == 0 ? this : new PageRequest(getPageNumber() - 1, getPageSize(), getSort());
}
//第一页
public Pageable first() {
return new PageRequest(0, getPageSize(), getSort());
}
}
我们发现,PageRequest提供了很多构造方法,根据实际情况灵活选择。下面看实现代码:
public void queryStudentByPage() {
//按分数倒序排列
Sort sort = new Sort(Sort.Direction.DESC,"score");
//构造PageRequest分页条件,第一页、每页10行、排序条件
PageRequest pageRequest = new PageRequest(0,10, sort);
Page page = studentRepo.findAll(pageRequest);
List studentEntities = page.getContent();
for (StudentEntity studentEntity : studentEntities) {
System.out.println(studentEntity.toString());
}
}
查询结果如下:
Hibernate:
select
studentent0_.id as id1_0_,
studentent0_.address as address2_0_,
studentent0_.birthday as birthday3_0_,
studentent0_.name as name4_0_,
studentent0_.school as school5_0_,
studentent0_.score as score6_0_,
studentent0_.tel as tel7_0_
from
t_student studentent0_
order by
studentent0_.score desc limit ?
Hibernate:
select
count(studentent0_.id) as col_0_0_
from
t_student studentent0_
StudentEntity{id='6c09a952f5b9474fb56996db642e7bab', name='沙鸿飞', address='玉龙小区', tel='12314512312311', school='青大附中', birthday='2001-03-01', score=99}
StudentEntity{id='c46800036ea94caea07c1f2b90576c2f', name='赵继峰', address='菜市场', tel='12314512312311', school='大庆中学', birthday='2002-03-11', score=99}
StudentEntity{id='6b2bc83ff6ea4f7aa95986e3eeb1883f', name='赵六', address='玉龙小区', tel='12314512312311', school='青大附中', birthday='2001-03-01', score=98}
StudentEntity{id='76a5fad795aa4605b43daf9c5f4e8edd', name='张逸杰', address='菜市场', tel='12314512312311', school='胜利中学', birthday='2002-03-11', score=98}
StudentEntity{id='81fbeb9e7e8749e78c2495e169766274', name='吕春芳', address='柏景湾', tel='12314512312311', school='实验中学', birthday='2000-03-11', score=98}
StudentEntity{id='b6ef1f42e8a64367abc251af22246870', name='郎芬', address='菜市场', tel='12314512312311', school='西城中学', birthday='2001-03-11', score=98}
StudentEntity{id='bc56bad3fd4e4604abe8a1c4ee2c1f66', name='李海峰', address='菜市场', tel='12314512312311', school='明湖中学', birthday='2002-02-11', score=98}
StudentEntity{id='ded2215cfbb846d296aece2531bce6b8', name='赵九', address='岩石寨', tel='12314512312311', school='中山一小', birthday='2001-01-01', score=98}
StudentEntity{id='e838a9fbbd4240d5a0922d1112b2171d', name='钱十', address='南淮安', tel='12314512312311', school='西城中学', birthday='2001-03-31', score=98}
StudentEntity{id='babee95b37c04db38c0e74d923521ec5', name='钱十', address='南淮安', tel='12314512312311', school='山大附中', birthday='2001-03-11', score=89}
通过控制台打印出的sql我们发现里面通过limit限定返回从第几行到第几行的数据,另外发现不光查询了前10行的数据,还统计了总条数。那是因为返回的结果Page提供getTotalPages(获取总页数)、getTotalElements(获取总行数)等方法,需要在查询的时候获取总的数据行数。