В MongoDB, как рассчитать среднее значение ($ avg) для класса ($ group) после объединения нескольких коллекций ($ lookup) - PullRequest
0 голосов
/ 16 марта 2020

Здесь у меня есть две коллекции:

conso

{   
  "_id" : ObjectId("5684f3c454b1fd6926c322fd"),
  "client" : "1",
  "conso" : "4"
}
{
  "_id" : ObjectId("56d82612b63f1f31cf906003"),
  "client" : "1",
  "conso" : "2"
}
{ 
  "_id" : ObjectId("56d82612b63f1c31cf906004"),
  "client" : "2",
  "conso" : "10"
}
{
  "_id" : ObjectId("59301c39028afaf3450e2890"),
  "client" : "2",
  "conso" : "20"
}
{
  "_id" : ObjectId("59301c39029afaf4450e2885"),
  "client" : "3",
  "conso" : "18"
}
{
  "_id" : ObjectId("59301c39030afaf4450e2885"),
  "client" : "3",
  "conso" : "12"
}

class

{
  "_id" : ObjectId("5f6d219d345f0066299c1fd6"),
   "CLIENT" : "1",
   "class" : "A"
}    
{ 
  "_id" : ObjectId("5e6d219c345f0066299c1fd6"),
   "CLIENT" : "2",
   "class" : "A"
}
{
  "_id" : ObjectId("5e6d02c97d9426227fa00401"),
   "CLIENT" : "3",
   "class" : "B"
}

Я хотел бы иметь:

{"class" : "A", avg : 9}

{"class" : "B", avg : 15}

Мой код:

db.conso.aggregate([
    {$group: {_id : {class: "$class"}, avg: { $avg: "$conso" }}},
    {$lookup: {from: "class", localField: "client", foreignField: "CLIENT", as: "class_info"}}
    ]);

и я получаю:

{ "_id" : { "class" : null }, "avg" : 11, "class_info" : [ ] }

1 Ответ

0 голосов
/ 16 марта 2020

После внесения указанных ниже изменений в вашу коллекцию conso и ваш запрос мы можем получить желаемый результат.

Изменение в conso коллекции

Атрибут conso в коллекции conso принимает строковое значение, которое нам нужно изменить на число, поэтому измененная коллекция будет выглядеть так:

{"_id":"5684f3c454b1fd6926c322fd","client":"1","conso":4},
{"_id":"56d82612b63f1f31cf906003","client":"1","conso":2},
{"_id":"56d82612b63f1c31cf906004","client":"2","conso":10},
{"_id":"59301c39028afaf3450e2890","client":"2","conso":20},
{"_id":"59301c39029afaf4450e2885","client":"3","conso":18},
{"_id":"59301c39030afaf4450e2885","client":"3","conso":12}

Если вы не хотите изменять свою коллекцию, вы можете использовать $ toInt чтобы преобразовать строку conso в число, этот шаг добавит еще один этап конвейера ( $ project ) к нашему существующему запросу между $ lookup и $ group. Обратите внимание, что $ toInt будет выдавать ошибку, если значение не может быть преобразовано в int.

Изменение запроса

Выполните команду $lookup сначала выполните, а затем выполните $group, а на групповом этапе _id необходимо изменить с class: "$class" на class: "$class_info.class"

Измененный запрос будет

db.conso.aggregate([
    { $lookup: { 
       from: "class",
       localField: "client", 
       foreignField: "CLIENT", 
       as: "class_info"}
    }, 
    { $group: {_id : {class: "$class_info.class"}, avg: { $avg: "$conso" }}},
]);

Надеюсь, это поможет!

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...