Mongodb aggregate -排序然后获取周围的文档

t8e9dugd  于 2023-04-20  发布在  Go
关注(0)|答案(1)|浏览(128)

我尝试编写一个mongodb聚合来应用2级排序,然后获取排序集中某个特定文档前后的2个文档
文档插入顺序错误:

db.test.insertMany([
   { name: 'V', type: 'Trap' }, 
   { name: 'J', type: 'Magic' },
   { name: 'B', type: 'Effect' }
])

要在每个type中按字母顺序排序,我可以这样做:

db.test.aggregate([{ "$sort": { type: 1, name: 1 } }])

Result:
{ name: 'B', type: 'Effect' }
{ name: 'J', type: 'Magic' }
{ name: 'V', type: 'Trap' }

我尝试使用以下查询(带替换)来获取“after”文档:

[
  { $sort: { type: 1, name: 1 } },
  {
    $match: {
      name: {
        $gt: <name>,
      },
      type: {
        $gte: <type>,
      },
    },
  },
  { $limit: 1 }
]

例如:
文件{ name: 'K', type: 'Trap' }应在J和V之间。

  • 上面的查询正确地给出了“V”。

文件{ name: 'C', type: 'Effect' }应在B和J之间传递。

  • 上面的查询正确地给出了“J”。

但是,文档{ name: 'K', type: 'Effect' }也需要在B和J之间进行,因为它应该保留在“Effect”分组中。

  • 查询再次错误地返回“V”(应该是J)。

删除$match属性中的任何一个都会在其他情况下产生不正确的结果。似乎也不能在所有情况下使用$and/or来获得正确的结果
相反,我的“before”查询如下(并非在所有情况下都有效):

{ $sort: { type: -1, name: -1 } },
            {
               $match: {
                  name: { $lt: card.name },
                  type: { $lte: card.type }
               }
            },
{ $limit: 1 }
0x6upsns

0x6upsns1#

我可以写一个匹配查询,它检查or条件,其中检查type是否大于给定的类型,或者如果类型等于给定的类型,则检查name是否大于给定的名称。要获得之前的文档,请将gt替换为lt

db.collection.aggregate([
  { $sort: { type: 1, name: 1 } },
  {
    $match: {
      $or: [
        { type: { $gt: <type> } },
        { $and: [{ type: <type> }, { name: { $gt: <name> } }] }
      ]
    }
  },
  { $limit: 1 }
])

playground

相关问题