При использовании MongoDB я в настоящее время делаю условное обновление как часть процесса агрегирования в форме (упрощенно):
db.dbname.update({attr1 : value1, attr2 : value2},
{"$inc" : { avg : current_value, nr : 1}},
false (multi), true (upsert))
Но я хочу также сохранить максимальное (и минимальное) значение без необходимости извлечения документа. Что-то вроде:
db.dbname.update({ attr1 : value1, attr2 : value2},
{"$inc" : { avg : current_value, nr : 1},
"$setIfBigger" : { max : current_value}},
false (multi), true (upsert))
Возможно ли это эффективным способом?
Мое текущее, крайне неэффективное решение состоит в том, что я проверяю текущий документ агрегации, и, если он существует, я соответствующим образом обновляю значения, а если нет, я создаю новый документ. Пример (опять же, много упрощено, но суть есть):
var obj = db.dbname.findOne({attr1 : value1, attr2 : value2},{_id:1});
if (obj != null) {
db.dbname.update({attr1 : value1, attr2 : value2},
{"$inc" : { avg : current_value, nr : 1},
"$set" : { max : (obj.max > current_value ? obj.max : current_value}},
false (multi), true (upsert));
} else {
db.dbname.save({attr1 : value1, attr2 : value2,
avg : current_value, nr : 1,
max : current_value});
}
Реальная программа написана на Java и использует mongo-API, а процесс агрегирования довольно сложен и использует методы компоновки, выходящие за рамки Javascript, для взаимодействия с другими серверами, поэтому ergo mapreduce не подходит. Наконец, конечный результат - это огромный набор простых значений, которые я хочу сохранить наиболее эффективным способом, а также сохранить предварительно рассчитанные средние, максимумы и минимумы определенных комбинаций.
Одним из решений является создание уникальных объектов-функций в JS для каждого отдельного обновления, что, по моему мнению, не является эффективным способом?
Основная цель - сократить время, необходимое для выполнения агрегации этого типа, использование полосы пропускания является вторичным.