Saltar al contenido principal
Tema

8 métodos de los arrays, como usarlos y hacer tu propio polyfill

5 minutos de lectura

Índice

Los arrays tienes una buena cantidad de métodos que nos facilitan ciertos procedimientos y nos permiten tener un código más limpio. Explicaremos como funcionan y como hacer nuestros propios polyfills.

Crear tus propios métodos

Los métodos están en el prototype del objeto global Array, podemos modificar este y añadir nuestros propios métodos para luego usarlos en cualquier array.

Debemos usar una función expresada y usar this, que será el array al cual estamos ejecutando el método.

1Array.prototype.awesomeMethod = function() {
2 // Imprime el array en el que ejecutamos el método
3 console.log(this)
4}
5
6const numbers = [1, 2, 3]
7
8numbers.awesomeMethod() // [1, 2, 3]

Y así podemos crear nuestros propios métodos. Luego de saber esto, seguiremos con los métodos propios del lenguaje.

forEach

El forEach itera el array y ejecuta el callback que le pasemos.

El callback recibe el elemento actual (obligatorio), el índice y el array entero.

1const numbers = [1, 2, 3, 4, 5]
2
3numbers.forEach((number) => console.log(number)) // 1, 2, 3, 4, 5

Para hacer el polyfill simplemente tenemos que hacer un bucle for y ejecutar el callback.

1Array.prototype.forEach = function(callback) {
2 for (let i = 0; i < this.length; i++) {
3 // Ejecutamos el callback y le pasamos los parámetros
4 callback(this[i], i, this)
5 }
6}

map

El map nos crea un nuevo array con los elementos transformados de acuerdo al callback que recibe y nos lo retorna.

El callback recibe el elemento actual (obligatorio), el índice y el array entero.

1const numbers = [1, 2, 3, 4, 5]
2
3const transformedNumbers = numbers.map((number) => number * 2)
4
5console.log(transformedNumbers) // [2, 4, 6, 8, 10]

Para hacer el polyfill tenemos que crear un nuevo array, iterar el array original y por cada elemento ejecutar el callback, el elemento transformado que nos retorne el callback, lo añadiremos al array que creamos para finalmente retornarlo.

1Array.prototype.map = function(callback) {
2 const storage = []
3
4 for(let i = 0; i < this.length; i++){
5 // Guardamos el elemento que nos retorne el callback
6 const transformedElement = callback(this[i], i, this)
7 // Lo añadimos al array
8 storage.push(transformedElement)
9 }
10
11 return storage
12}

filter

El filter crea un nuevo array con los elementos que cumplan la condición que establece el callback y nos lo retorna.

El callback recibe el elemento actual (obligatorio), el índice y el array entero.

1const numbers = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
2
3// Filtra los números pares
4const evens = numbers.filter((number) => number % 2 === 0)
5
6console.log(evens) // [2, 4, 6, 8, 10]

Para hacer el polyfill tenemos que crear un nuevo array, iterar el array original y ejecutar el callback, si nos retorna truthy, añadiremos el elemento al array que creamos para finalmente retornar el array creado.

1Array.prototype.filter = function(callback) {
2 const storage = []
3
4 for(let i = 0; i < this.length; i++){
5 // Guardamos el elemento actual
6 const currentElement = this[i]
7
8 // Ejecutamos el callback y si es truthy añadimos el elemento
9 if(callback(currentElement, i, this)) {
10 storage.push(currentElement)
11 }
12 }
13
14 return storage
15}

reduce

El reduce itera el array original, acumula el valor que retornemos con el callback que le pasemos y nos retorna el acumulador. El método como segundo parámetro recibe el valor inicial del acumulador, en caso de no especificarse el valor será el elemento de la primera posición del array.

El callback recibe el acumulador y el elemento actual.

1// Array con los gastos
2const expenses = [150, 200, 700, 10, 600]
3
4// Nos calcula el total de todos los gastos
5const total = expenses.reduce((accumulator, number) => accumulator + number)
6
7console.log(total) // 1660 ✅

Para hacer el polyfill tenemos que revisar si el método recibio un valor inicial, si lo recibió el valor del primer índice que usaremos para iterar el array, será de 0, si no lo recibió el valor será de 1 y valor del accumulator será el del primer elemento del array, luego debemos iterar el array, asignar el valor que retorne el callback al acumulador y al final retornarlo.

1Array.prototype.reduce = function(callback, accumulator) {
2 const firstIndex = accumulator ? 0 : 1
3
4 if(!accumulator) accumulator = this[0]
5
6 for(let i = firstIndex; i < this.length; i++){
7 // Le asignamos al acumulador lo que nos retorne el callback
8 accumulator = callback(accumulator, this[i])
9 }
10
11 return accumulator
12}

find

El find retorna el primer elemento que encuentre dentro del array que cumpla la condición que establece el callback, en caso que ningún elemento cumpla la condición, nos retorna undefined.

1const prices = [100, 500, 200, 800, 50, 600, 1200]
2
3const firstExpensivePrice = prices.find((price) => price > 650)
4
5console.log(firstExpensivePrice) // 800 ✅

Para hacer el polyfill tenemos que iterar el array original, ejecutar el callback y si nos retorna truthy, retornamos el elemento. En caso que no lo encuentre no es necesario retornar undefined al final puesto que es el valor por defecto cuando no retornamos nada.

1Array.prototype.find = function(callback) {
2 for(let i = 0; i < this.length; i++){
3 // Guardamos el elemento actual
4 const currentElement = this[i]
5
6 // Ejecutamos el callback y si es truthy retornamos el elemento actual
7 if(callback(currentElement, i, this)){
8 return currentElement
9 }
10 }
11}

every

Este revisa que todos los elementos de un array cumplan una condición que establece el callback y nos devuelve un booleano.

1const isEven = (number) => number % 2 === 0
2
3const numbers = [2, 4, 6, 8, 10, 12]
4
5console.log(numbers.every(isEven)) // true
6
7const numbers2 = [1, 2, 3, 4, 5 ,6]
8
9console.log(numbers2.every(isEven)) // false

Para hacer el polyfill tenemos que iterar el array original, ejecutar el callback con los parámetros y si nos retorna falsy, retornamos false, en caso que todos los elementos terminen retornando truthy, retornamos true.

1Array.prototype.every = function(callback) {
2 for(let i = 0; i < this.length; i++) {
3 // Ejecutamos el callback y si es falsy retornamos false
4 if(!callback(this[i], i, this)) return false
5 }
6
7 return true
8}
9

some

El some revisa si al menos un elemento del array, cumple la condición que establece el callback y nos devuelve un booleano.

El callback recibe el elemento actual (obligatorio), el índice y el array entero.

1const numbers = [0, 12, 50, 8, 9, 15]
2
3// Revisa si un elemento es múltiplo de 5
4
5console.log(numbers.some((number) => number % 5 === 0)) // true
6
7
8// Revisa si un elemento es múltiplo de 7
9
10console.log(numbers.some((number) => number % 7 === 0)) // false

Para hacer el polyfill tenemos que iterar el array, ejecutar el callback y si retorna truthy, retornamos true, en caso que ningún elemento termine retornando truthy, retornamos false al final.

1Array.prototype.some = function(callback) {
2 for(let i = 0; i < this.length; i++){
3 // Ejecutamos el callback y si es truthy retornamos true
4 if(callback(this[i], i, this)) return true
5 }
6
7 return false
8}

findIndex

El findIndex nos retorna el índice del primer elemento que cumpla la condición que establece el callback, si no encuentra ningún elemento nos retorna -1.

1const numbers = [1, 0, 3, 4, 10 ,6]
2
3console.log(numbers.findIndex((number) => number % 2 == 0)) // 3

Para hacer el polyfill tenemos que iterar el array, ejecutar el callback y si retorna truthy, retornamos el índice, en caso que ningún elemento termine retornando truthy, retornamos -1 al final.

1Array.prototype.findIndex = function(callback) {
2 for(let i = 0; i < this.length; i){
3 // Ejecutamos el callback y es truthy retornamos el índice
4 if(callback(this[i]), i, this)) return i
5 }
6
7 return -1
8}

Conclusión

Como podemos ver son métodos bastantes útiles y prácticos de usar. Hacer nuestros polyfills nos ayudan a ver y entender mucho mejor la lógica detrás de cada método.