Перевести операцию агрегирования из MongoDB в MapReduce - PullRequest
1 голос
/ 05 мая 2020

Я уже несколько дней пытаюсь перевести этот запрос в MapReduce. В частности, мне нужно выяснить, сколько разных автомобилей проехали «N» километров.

Запрос:

db.adsb.group({
    "key": {
        "KM": true
    },
    "initial": {
        "countCar": 0
    },
    "reduce": function(obj, prev) {
        if (obj.Matricula != null) if (obj.Matricula instanceof Array) prev.countCar += obj.Matricula.length;
        else prev.countCar++;
    },
    "cond": {
        "KM": {
            "$gt": 10000,
            "$lt": 45000
        }
    }
});

Каждый документ в Mon go имеет такую ​​форму:

{
        "_id" : ObjectId("5a8843e7d79a740f272ccc0a"),
        "KM" : 45782,
        "Matricula" : "3687KTS",
}

Я пытаюсь получить что-то вроде:

 /* 0 */
 {
     “KM” : 45000,
     “total” : 634
 }

 /* 1 */
 {
     “KM” : 46000,
     “total” : 784
 }

Мой код ниже, и он компилируется, но не дает ожидаемых результатов.

В частности, каждый раз, когда я вхожу в «уменьшить», кажется, что все значения сбрасываются на 0, что не позволяет мне накапливать регистрации. Одна из моих проблем заключается в том, что при обработке больших объемов информации функция должна несколько раз повторять «сокращение». Я также не знаю, можно ли это сделать таким образом, или мне нужно было бы вернуть список автомобильных номеров и их счетчик вместе в «уменьшить»; а затем в финальной стадии сложите все это.

// Map function
var m = function() {
  if (this.KM > 10000 && this.KM < 45000) { // So that i can get KM grouped together by thousands (10000, 20000, 30000...)
    var fl = Math.round(this.KM / 1000) * 1000;
    var car = this.Matricula
    emit (fl, car);
    //print("map KM=" + fl + " Matricula= " + car);
  }
};

// Reduce function
var r = function(key, values) {
    var ya_incluido = false;
    var cars_totales = 0;
    var lista_car = new Array();

    //print( key + " ---- " + values);

    for (var i=0; i < values.length;i++)
    {
            for (var j=0; j < lista_car.length;j++)
            {
                    if(values[i] == lista_car[j]) { //If it is already included, don't aggregate it
                            ya_incluido = true;
                    }

            } if (ya_incluido != true) { //If it is not included, add it to lista_av list.
                    lista_car.push(values[i]);
            } ya_incluido = false;
    }

    cars_totales = lista_av.length; //The number of distinct cars is equal to the lenght of the list we created
    return cars_totales;

};


// Finalize function
var f = function(key,value) {
  // Sum up the results?

}


db.runCommand( {
                 mapReduce: "dealer",
                 map: m,
                 reduce: r,
                 finalize: f,
                 out: {replace : "result"}
               } );

Я нашел здесь ответ и действительно хорошее объяснение: { ссылка }

1 Ответ

0 голосов
/ 06 мая 2020

Я нашел здесь ответ и действительно хорошее объяснение: { ссылка }

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

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