programing

Mongodb 집계 파이프라인 그룹 푸시를 제한하는 방법

topblog 2023. 6. 22. 21:24
반응형

Mongodb 집계 파이프라인 그룹 푸시를 제한하는 방법

집계 파이프라인을 사용하여 그룹 함수에서 푸시된 요소의 양을 제한할 수 없습니다.이것이 가능합니까?작은 예:

데이터:

[
    {
        "submitted": date,
        "loc": { "lng": 13.739251, "lat": 51.049893 },
        "name": "first",
        "preview": "my first"
    },
    {
        "submitted": date,
        "loc": { "lng": 13.639241, "lat": 51.149883 },
        "name": "second",
        "preview": "my second"
    },
    {
        "submitted": date,
        "loc": { "lng": 13.715422, "lat": 51.056384 },
        "name": "nearpoint2",
        "preview": "my nearpoint2"
    }
]

통합 파이프라인은 다음과 같습니다.

var pipeline = [
    //I want to limit the data to a certain area
    { $match: {
        loc: {
            $geoWithin: {
                $box: [
                    [locBottomLeft.lng, locBottomLeft.lat],
                    [locUpperRight.lng, locUpperRight.lat]
                ]
            }
        }
    }},
    // I just want to get the latest entries  
    { $sort: { submitted: -1 } },
    // I group by name
    {
      $group: {
          _id: "$name",
          // get name
          submitted: { $max: "$submitted" },
          // get the latest date
          locs: { $push: "$loc" },
          // push every loc into an array THIS SHOULD BE LIMITED TO AN AMOUNT 5 or 10
          preview: { $first: "$preview" }
      }
    },
    // Limit the query to at least 10 entries.
    { $limit: 10 }
];

어떻게 제한할 수 있습니까?locs에 대한 배열.10아니면 다른 사이즈는?나는 무엇인가를 시도했습니다.$each그리고.$slice하지만 그것은 효과가 없는 것 같습니다.

왼쪽 아래 좌표와 오른쪽 위 좌표가 각각 다음과 같다고 가정합니다.[0, 0]그리고.[100, 100]MongoDB 3.2에서 연산자를 사용하여 원하는 배열의 하위 집합을 반환할 수 있습니다.

db.collection.aggregate([
    { "$match": { 
        "loc": { 
            "$geoWithin":  { 
                "$box": [ 
                    [0, 0], 
                    [100, 100]
                ]
            }
        }}
    }},
    { "$group": { 
        "_id": "$name",
        "submitted": { "$max": "$submitted" }, 
        "preview": { "$first": "$preview" }
        "locs": { "$push": "$loc" }
    }}, 
    { "$project": { 
        "locs": { "$slice": [ "$locs", 5 ] },
        "preview": 1,
        "submitted": 1
    }},
    { "$limit": 10 }
])

시작 위치Mongo 5.2새로운 집계 어큐뮬레이터의 완벽한 사용 사례입니다.

// { submitted: ISODate("2021-12-05"), group: "group1", value: "plop" }
// { submitted: ISODate("2021-12-07"), group: "group2", value: "smthg" }
// { submitted: ISODate("2021-12-06"), group: "group1", value: "world" }
// { submitted: ISODate("2021-12-12"), group: "group1", value: "hello" }
db.collection.aggregate([
  { $group: {
    _id: "$group",
    top: { $topN: { n: 2, sortBy: { submitted: -1 }, output: "$value" } }
  }}
])
// { _id: "group1", top: [ "hello", "world" ] }
// { _id: "group2", top: [ "smthg" ] }

이는 다음을 적용합니다.$topN다음과 같은 그룹 누적:

  • 각 그룹에 대해 상위 2개(n: 2) 요소
  • 정의된 상위 2개sortBy: { submitted: -1 }(시간순으로 표시됨)
  • 그룹화된 각 레코드에 대해 필드 추출value(output: "$value")

저는 (1) 그룹 단계에서 모든 값을 푸시할 수 있도록 허용한 다음, (2) 후속 $프로젝트 단계에 $filter를 추가하여 이 문제를 해결했습니다.$filter 내에서 결격값이 있는 모든 배열 멤버를 제거합니다.

https://docs.mongodb.com/manual/reference/operator/aggregation/filter/

통과하면 이를 달성할 수 있습니다.$slice운영자가 직접$push.

  var pipeline = [{
    //I want to limit the data to a certain area
    $match: {
        loc: {
            $geoWithin: {
                $box: [
                    [locBottomLeft.lng, locBottomLeft.lat],
                    [locUpperRight.lng, locUpperRight.lat]
                ]
            }
        }
    }
},
// I just want to get the latest entries  
{
    $sort: {
        submitted: -1
    }
},
// I group by name
{
    $group: {
        _id: "$name",
        < --get name
        submitted: {
            $max: "$submitted"
        },
        < --get the latest date
        locs: {
            $push: {
              $slice: 10
            }
        },
        < --push every loc into an array THIS SHOULD BE LIMITED TO AN AMOUNT 5 or 10
        preview: {
            $first: "$preview"
        }
    }
},
//Limit the query to at least 10 entries.
{
    $limit: 10
}
];

언급URL : https://stackoverflow.com/questions/24594049/mongodb-aggregation-pipeline-how-to-limit-a-group-push

반응형