Добавьте поле, которое является отображением другого в агрегате $ addFields mongo - PullRequest
1 голос
/ 14 марта 2019

У меня есть коллекция значений Mongo по метрикам, например:

[
    {"metric": "A", "value": 1.0},
    {"metric": "B", "value": 0.5}
]

Я хочу написать агрегированный запрос, который будет делать средневзвешенное значение, но вес каждой метрики нев коллекции - он динамически устанавливается в точке, в которой написан запрос.

Так что мне нужно добавить поле weight, отображающее поле метрики в некоторое значение типа double.Я пробовал это:

db.collection.aggregate([
    {
        $addFields: {
            metricWeight: {"A": 2.0, "B": 5.0}["$metric"]
        }
    }
])

т.е.пытаясь определить карту в строке как объект JS, а затем проиндексировать ее с полем metric - но это дает мне undefined как каждый metricWeight.

Ожидаемый результат этого этапа конвейерабудет:

[
    {"metric": "A", "value": 1.0, "metricWeight": 2.0},
    {"metric": "B", "value": 0.5, "metricWeight": 5.0}
]

Есть ли способ добиться этого с помощью агрегатного запроса Монго?

1 Ответ

1 голос
/ 14 марта 2019

Вы можете использовать ниже агрегации

const object = { "A": 2.0, "B": 5.0 }

db.collection.aggregate([
  { "$addFields": {
    "keys": {
      "$objectToArray": object
    }
  }},
  { "$project": {
    "metric": 1,
    "value": 1,
    "metricWeight": {
      "$arrayElemAt": [
        "$keys.v",
        { "$indexOfArray": ["$keys.k", "$metric"] }
      ]
    }
  }}
])
...