Suponiendo que tengo 2 matrices:
const products = [ { name: 'prod1', category: 'Meat' }, { name: 'prod2', category: 'Meat' }, { name: 'prod3', category: 'Dairy' }]; const rate = [ { name: 'prod1', rate: 23, }, { name: 'prod2', rate: 36 }, { name: 'prod3', rate: 50, }];¿Cómo obtendría la categoría que tiene la tasa de suma más alta? Por ejemplo, prod1 y prod2 comparten la misma categoría "Carne" y, por lo tanto, la tasa de carne es 36 + 23 = 59.
La forma en que lo pensé es crear una matriz ajustada de productos donde cada entrada contendrá la tasa de la segunda matriz y luego crearé una matriz de resultados y empujaré un objeto de categoría y sumRate después de iterar la matriz ajustada.
Entonces, si el resultado Array tiene un objeto con categoría, ajustaría la suma y agregaría la nueva tarifa, si no, crearé una nueva entrada con categoría: tarifa.
¿Podemos hacer esto de una manera muy óptima?
Como probablemente sabe el OP, la agrupación canónica es así...
const prodsByCategory = products.reduce((acc, p) => { let cat = p.category; if (!acc[cat]) acc[cat] = []; acc[cat].push(p); return acc; }, {});Modifique esto un poco para agregar los datos que serán necesarios para optimizar.
const prodsByCategory = products.reduce((acc, p) => { let cat = p.category; // instead of just an array, keep an array and a total if (!acc[cat]) acc[cat] = { products: [], totalRate: 0 }; // instead of just pushing, push and increment total with a lookup acc[cat].products.push(p); acc[cat].totalRate += rateForProduct(p) || 0; return acc; }, {});Necesitamos una búsqueda de rateForProduct, como esta:
const rateForProduct = product => { return rate.find(r => r.name === product.name)?.rate || 0; } Eso debería producir un objeto con clave por categoría con valores que tienen un accesorio llamado totalRate . Ordene esas entradas para que la primera esté maximizada. Aquí hay una demostración...
const products = [{ name: 'prod1', category: 'Meat' }, { name: 'prod2', category: 'Meat' }, { name: 'prod3', category: 'Dairy' } ]; const rate = [{ name: 'prod1', rate: 23, }, { name: 'prod2', rate: 36 }, { name: 'prod3', rate: 50, } ]; const rateForProduct = product => { return rate.find(r => r.name === product.name)?.rate || 0; } const prodsByCategory = products.reduce((acc, p) => { let cat = p.category; if (!acc[cat]) acc[cat] = { products: [], totalRate: 0 }; acc[cat].products.push(p); acc[cat].totalRate += rateForProduct(p); return acc; }, {}); const sortedEntries = Object.entries(prodsByCategory).sort((a, b) => b[1].totalRate - a[1].totalRate); const bestEntry = { category: sortedEntries[0][0], rate: sortedEntries[0][1].totalRate } console.log(bestEntry);