MongoDB 分頁查詢的總結
對於 mongodb 數據庫,和 mysql 類似,也有自帶的分頁 api,其實直接調用 api,也可以實現 mongodb 的分頁,主要 api 就是兩個:
query.skip((pageNum - 1) * pageSize);
query.limit(pageSize);
其中:pageNum:當前頁,pageSize:頁大小
但是當數據量多了的時候,mongodb 再使用這種方式去做分頁,查詢效率就會變得很慢,主要原因是 mongodb 自帶的這個 skip() 方法的問題,跳躍查詢導致雖然做了分頁,但還是會使數據查詢效率低下。
主要原理思路:
條件查詢+排序+限制返回記錄。
邊查詢,邊排序,排序之后,抽取第一次分頁中的最后一條記錄,作為第二次分頁的條件,進行條件查詢,以此類推…
假設現在要給一個 Title 類做分頁查詢,一開始還是傳統想法,必須要有“當前頁”和“頁大小”這兩個參數:
public List<Title> listDesc(int pageNum, int pageSize) {
List<Title> titleList;
Query query = new Query();
// 通過 _id 來排序
query.with(Sort.by(Sort.Direction.ASC, "_id"));
if (pageNum != 1) {
// number 參數是為了查上一頁的最后一條數據
int number = (pageNum - 1) * pageSize;
query.limit(number);
List<Title> titles = mongoTemplate.find(query, Title.class);
// 取出最后一條
Title title = titles.get(titles.size() - 1);
// 取到上一頁的最后一條數據 id,當作條件查接下來的數據
String id = title.get_id();
// 從上一頁最后一條開始查(大於不包括這一條)
query.addCriteria(Criteria.where("_id").gt(id));
}
// 頁大小重新賦值,覆蓋 number 參數
query.limit(pageSize);
// 即可得到第n頁數據
titleList = mongoTemplate.find(query, Title.class);
return titleList;
}
其實就是不要使用 mongodb 自帶的 skip() 這個方法,轉而使用 sort() 排序和 limit() 限制數據大小這兩個方法,通過排序,讓數據每次從上一頁的最后一條開始起做查詢,再限制每次返回的總數據大小即可!