Si tengo una matriz de números y quiero obtener el número más cercano al promedio, ¿cómo puedo obtener ese número?
Intenté ordenar la matriz en orden ascendente, y luego recuperé el elemento del medio, que es el promedio.
Nota: utilicé Math.floor() en caso de que la longitud de la matriz sea impar, no un número par
const arr = [1, 6, 10, 3, 15, 9, 4, 7]; const arrSorted = arr.sort((a,b)=>ab); const nearToAVG = arrSorted[Math.floor(arr.length/2)]; console.log(nearToAVG); // 7¿Hay mejores formas de acercar el número al promedio en la matriz?
Analicemos este problema. Desea el índice con el valor más cercano al promedio de los índices de la matriz. Para obtener eso, primero puede calcular la suma de la matriz. Conociendo la suma, puede hacer un segundo barrido de la matriz arr para tomar la diferencia de cada elemento del promedio y almacenarlo en una variable. Por último, actualizaría esa variable si la diferencia entre el promedio y el índice actual está más cerca de cero que el valor almacenado. Al final de la matriz, tendrá la respuesta que está buscando.
Aquí hay un ejemplo simple de lo anterior:
const arr = [1, 6, 10, 3, 15, 9, 4, 7]; // get average let sum = 0; for(let i = 0; i < arr.length; sum += arr[i], i++); let ave = sum / arr.length; // 6.875 function nearestIdxToAverage(array, average) { if(!array.length) return 0; // stores initial difference and gets replaced by index let nearest = Math.abs(array[0] - average); for(let i = 0; i < array.length; i++) { const diff = Math.abs(array[i] - average); // stores the offset of the diff closest to 0 (relative to the average) nearest = (diff < nearest)? i: nearest; } return nearest; } console.log(`average: ${ave}\nnearest idx: ${nearestIdxToAverage(arr, ave)}`); // average: 6.875 // nearest idx: 7Como señalé en un comentario a otra respuesta, este es uno de esos casos, cuando realmente necesita ser más preciso que el "promedio". La median y la mean son los promedios más comunes y, dependiendo de lo que quieras, puedes obtener diferentes respuestas. Por ejemplo, en [3, 20, 1, 4, 2] , la mediana es 3 , pero como la media es 6 , el valor original más cercano a la media es 4 .
Esta versión asume que desea obtener el valor en la matriz más cercana a la media aritmética de los números:
const closestToMean = (ns, m = ns .reduce ((a, b) => a + b, 0) / ns .length) => ns .reduce ((c, n) => Math .abs (n - m) < Math .abs (c - m) ? n : c, Infinity) console .log (closestToMean ([3, 20, 1, 4, 2])) console .log (closestToMean ([1, 6, 10, 3, 15, 9, 4, 7]))Sumamos los números y dividimos por su longitud para encontrar la media, luego doblamos la lista de números, manteniendo en cada etapa el más cercano a esa media.
De hecho, preferiría dividir esto y extraer las funciones auxiliares comunes sum , que totaliza una matriz de números, mean , que usa sum para calcular la media aritmética, y minimumBy , que encuentra el elemento más pequeño de una matriz, de acuerdo con el resultado de aplicar la función suministrada a cada elemento. Creo que esta versión es mucho más legible:
const sum = (ns) => ns .reduce ((a, b) => a + b, 0) const mean = (ns) => sum (ns) / ns .length const minimumBy = (fn) => (ns) => ns .reduce ((c, n) => fn (n) < fn (c) ? n : c, Infinity) const closestToMean = (ns, m = mean (ns)) => minimumBy (n => Math .abs (n - m)) (ns) console .log (closestToMean ([3, 20, 1, 4, 2])) console .log (closestToMean ([1, 6, 10, 3, 15, 9, 4, 7]))... y también nos hemos encontrado con algunas funciones útiles para usar en otras partes de este programa u otros.
Otro enfoque para lograr eso Mediante el uso de:
reduce para acumular la suma y dividirla por su longitud para obtener el promedio .
map iterar sobre esa matriz y devolver cada número con su nearByAVG (distancia entre ese número y el promedio) .
sort por esa propiedad en orden ascendente y obtenga el primero que tenga la distancia mínima al promedio.
const arr = [1, 6, 10, 3, 15, 9, 4, 7]; const sum = arr.reduce((acc, curr)=>acc+curr); const avg = sum/arr.length; const arrMaped = arr.map(num=>({num,nearByAVG: Math.abs(num-avg)})); const arrSorted = arrMaped.sort((a,b)=>a.nearByAVG-b.nearByAVG); console.log(arrSorted[0].num)