Docs Menu
Docs Home
/ /
Map-Reduce
/ / /

Solucionar problemas de la función Reduce

Nota

Canalización de agregación como alternativa a Map-Reduce

A partir de MongoDB 5.0, map-reduce está obsoleto:

Para ejemplos de alternativas de pipeline de agregación a map-reduce, consulte:

Una canalización de agregación también es más fácil de solucionar que una operación de mapa-reducción.

La reduce función es una función de JavaScript que reduce a un solo objeto todos los valores asociados a una clave específica durante una operación de map-reduce. La reduce función debe cumplir varios requisitos. Este tutorial ayuda a verificar que la reduce función cumple los siguientes criterios:

  • La reduce función debe devolver un objeto cuyo tipo debe ser idéntico al tipo del value emitido por la map función.

  • El orden de los elementos en valuesArray no debe afectar la salida de la función reduce.

  • La reduce función debe ser idempotente.

Para obtener una lista de todos los requisitos para la reduce función, consulte mapReduce o mongosh el método db.collection.mapReduce() auxiliar.

Puede probar que la función reduce devuelve un valor que es del mismo tipo que el valor emitido por la función map.

  1. Define una función reduceFunction1 que toma los argumentos keyCustId y valuesPrices. valuesPrices es una matriz de números enteros:

    var reduceFunction1 = function(keyCustId, valuesPrices) {
    return Array.sum(valuesPrices);
    };
  2. Define una matriz de muestra de números enteros:

    var myTestValues = [ 5, 5, 10 ];
  3. Invocar reduceFunction1 con myTestValues:

    reduceFunction1('myKey', myTestValues);
  4. Verifique que reduceFunction1 haya devuelto un entero:

    20
  5. Define una función reduceFunction2 que toma los argumentos keySKU y valuesCountObjects. valuesCountObjects es una matriz de documentos que contienen dos campos count y qty:

    var reduceFunction2 = function(keySKU, valuesCountObjects) {
    reducedValue = { count: 0, qty: 0 };
    for (var idx = 0; idx < valuesCountObjects.length; idx++) {
    reducedValue.count += valuesCountObjects[idx].count;
    reducedValue.qty += valuesCountObjects[idx].qty;
    }
    return reducedValue;
    };
  6. Defina una matriz de muestra de documentos:

    var myTestObjects = [
    { count: 1, qty: 5 },
    { count: 2, qty: 10 },
    { count: 3, qty: 15 }
    ];
  7. Invocar reduceFunction2 con myTestObjects:

    reduceFunction2('myKey', myTestObjects);
  8. Verifique que reduceFunction2 haya devuelto un documento con exactamente los campos count y qty:

    { "count" : 6, "qty" : 30 }

La función reduce toma como argumento una matriz key y una values. Puede comprobar que el resultado de la función reduce no depende del orden de los elementos en la matriz values.

  1. Define una matriz de muestra values1 y una matriz de muestra values2 que solo difieren en el orden de los elementos de la matriz:

    var values1 = [
    { count: 1, qty: 5 },
    { count: 2, qty: 10 },
    { count: 3, qty: 15 }
    ];
    var values2 = [
    { count: 3, qty: 15 },
    { count: 1, qty: 5 },
    { count: 2, qty: 10 }
    ];
  2. Define una función reduceFunction2 que toma los argumentos keySKU y valuesCountObjects. valuesCountObjects es una matriz de documentos que contienen dos campos count y qty:

    var reduceFunction2 = function(keySKU, valuesCountObjects) {
    reducedValue = { count: 0, qty: 0 };
    for (var idx = 0; idx < valuesCountObjects.length; idx++) {
    reducedValue.count += valuesCountObjects[idx].count;
    reducedValue.qty += valuesCountObjects[idx].qty;
    }
    return reducedValue;
    };
  3. Invoque primero reduceFunction2 con values1 y luego con values2:

    reduceFunction2('myKey', values1);
    reduceFunction2('myKey', values2);
  4. Verifique que reduceFunction2 haya devuelto el mismo resultado:

    { "count" : 6, "qty" : 30 }

Como la operación map-reduce puede llamar a reduce varias veces para la misma clave, y no llamará a un reduce para instancias individuales de una clave en el conjunto de trabajo, la función reduce debe devolver un valor del mismo tipo que el valor emitido por la función map. Puedes probar que la función reduce procesa valores "reducidos" sin afectar el valor final.

  1. Define una función reduceFunction2 que toma los argumentos keySKU y valuesCountObjects. valuesCountObjects es una matriz de documentos que contienen dos campos count y qty:

    var reduceFunction2 = function(keySKU, valuesCountObjects) {
    reducedValue = { count: 0, qty: 0 };
    for (var idx = 0; idx < valuesCountObjects.length; idx++) {
    reducedValue.count += valuesCountObjects[idx].count;
    reducedValue.qty += valuesCountObjects[idx].qty;
    }
    return reducedValue;
    };
  2. Definir una clave de muestra:

    var myKey = 'myKey';
  3. Defina una matriz de muestra valuesIdempotent que contenga un elemento que sea una llamada a la función reduceFunction2:

    var valuesIdempotent = [
    { count: 1, qty: 5 },
    { count: 2, qty: 10 },
    reduceFunction2(myKey, [ { count:3, qty: 15 } ] )
    ];
  4. Define una matriz de muestra values1 que combina los valores pasados ​​a reduceFunction2:

    var values1 = [
    { count: 1, qty: 5 },
    { count: 2, qty: 10 },
    { count: 3, qty: 15 }
    ];
  5. Invoque el reduceFunction2 primero con myKey y valuesIdempotent y luego con myKey y values1:

    reduceFunction2(myKey, valuesIdempotent);
    reduceFunction2(myKey, values1);
  6. Verifique que reduceFunction2 haya devuelto el mismo resultado:

    { "count" : 6, "qty" : 30 }

Volver

Mapa de solución de problemas

En esta página