MongoDB-基于非唯一字段的分页

MongoDB-基于非唯一字段的分页,mongodb,Mongodb,我熟悉在大型MongoDB集合上进行分页的最佳实践,但是我正在努力弄清楚如何对排序值位于非唯一字段上的集合进行分页 例如,我有一个很大的用户集合,其中有一个字段表示他们做某事的次数。此字段定义为非唯一字段,可能包含具有相同值的大型文档组 我想返回按“numTimesDoneSomething”字段排序的结果 以下是一个示例数据集: {_id: ObjectId("50c480d81ff137e805000003"), numTimesDoneSomething: 12} {_id: Object

我熟悉在大型MongoDB集合上进行分页的最佳实践,但是我正在努力弄清楚如何对排序值位于非唯一字段上的集合进行分页

例如,我有一个很大的用户集合,其中有一个字段表示他们做某事的次数。此字段定义为非唯一字段,可能包含具有相同值的大型文档组

我想返回按“numTimesDoneSomething”字段排序的结果

以下是一个示例数据集:

{_id: ObjectId("50c480d81ff137e805000003"), numTimesDoneSomething: 12}
{_id: ObjectId("50c480d81ff137e805000005"), numTimesDoneSomething: 9}
{_id: ObjectId("50c480d81ff137e805000006"), numTimesDoneSomething: 7}
{_id: ObjectId("50c480d81ff137e805000007"), numTimesDoneSomething: 1}
{_id: ObjectId("50c480d81ff137e805000002"), numTimesDoneSomething: 15}
{_id: ObjectId("50c480d81ff137e805000008"), numTimesDoneSomething: 1}
{_id: ObjectId("50c480d81ff137e805000009"), numTimesDoneSomething: 1}
{_id: ObjectId("50c480d81ff137e805000004"), numTimesDoneSomething: 12}
{_id: ObjectId("50c480d81ff137e805000010"), numTimesDoneSomething: 1}
{_id: ObjectId("50c480d81ff137e805000011"), numTimesDoneSomething: 1}

如何返回按“numTimesDoneSomething”排序的数据集,每页有2条记录?

您可以在多个字段上排序,在这种情况下,可以在
numTimesDoneSomething
id
字段上排序。由于id_uu字段本身已根据插入时间戳升序,因此您将能够在集合中分页,而无需迭代重复数据,除非在迭代过程中插入新数据

db.collection.find().sort({numTimesDoneSomething:-1, _id:1}).offset(index).limit(2)

@cubbuk使用
offset
skip
)展示了一个很好的示例,但您也可以对他显示的查询进行建模,以实现范围分页:

db.collection.find().sort({numTimesDoneSomething:-1, _id:1})
由于此处的
\u id
是唯一的,并且您正在对其进行附议,因此实际上您可以通过
\u id
进行范围调整,并且结果,即使是在两个记录之间的
numTimesDoneSomething
12
,也应该是在一页上还是在下一页上保持一致

所以做一些简单的事情

var q = db.collection.find({_id: {$gt: last_id}}).sort({numTimesDoneSomething:-1, _id:1}).limit(2)

应该可以很好地进行范围分页。

不会
查找({u id:last\u id})
只返回一条记录?查找查询需要大于last\u id,不是吗?您的解决方案还涵盖了新插入+1的情况=)@AdamDuro Nice spot:)立即修复了此问题抱歉,重新定义此答案,但这不可能是正确的。对_id进行二次排序并不妨碍具有旧id的文档稍后在分页中出现。如果您只是查询$gt最后一个id,您将丢弃所有可能有较少numtime的旧文档。要使其工作,我相信您需要查询
$或:[{numtimes:last\u numtimes,\u id:last\u id},{numtimes:{$lt:last\u numtimes}}
,请原谅代码的解释。如果我不正确,请惩罚我。我目前正在努力解决非唯一范围分页的问题,我正在寻找答案。@Sammaye是的,但是_id只是次要排序,并且只有在
numX
相同的情况下才会影响顺序。结果很可能看起来像
{numX:2,{u id:2},{numX:2,{u id:3},{numX:1,{u id:1}
。在这种情况下,如果您的页面在第二个文档结束,将导致一个
\u id>3
的“下一页”查询,这将抛出第三个结果。在真正的查询中,您将抛出更多。