Эти три функции важны при выполнении функционального программирования в JS. В последнее время я работаю над курсом Алгоритмы и структуры данных JavaScript от FreeCodeCamp. Тем не менее, эти три немного сбивают с толку, поэтому вот заметки для обучения.

В мире функционального программирования (FP) эти функции широко используются для замены цикла for и цикла while для реализации изменений в каждом элементе массива или что-то в этом роде. Я нашел отличное выступление о концепции FP, которое стоит посмотреть. Очень рекомендую всем, кто только начинает.

Прежде чем погрузиться в функции, вот интересный рисунок, которым я хотел бы поделиться — забавный способ проиллюстрировать карту и уменьшить.

map()

.map() или Array.prototype.map() — это функция, которая может взаимодействовать со всеми элементами массива и возвращать массив в конце. Во-первых, в качестве примера возьмем наиболее понятный способ использования map().

const newArray= originalArray.map(itemInArray=>action)

Возьмите пример:

// original array
const arr = [1,3,5,7,9]
// newArr is the new array
// a can be anything
// just like when you doing for ...in while programming Python script
// here is to compare every item with 3 and return boolean 
const newArr = arr.filter(a=>a>3);
return newArr;

Он вернет массив [false, false, true, true, true], потому что здесь все элементы будут сравниваться с 3, и если оно больше 3, возвращать true.

Это один из основных форматов, и map() может делать больше. Синтаксис, скопированный из mdn, показан ниже.

// Arrow function
map((element) => { /* ... */ })
map((element, index) => { /* ... */ })
map((element, index, array) => { /* ... */ })

// Callback function
map(callbackFn)
map(callbackFn, thisArg)

// Inline callback function
map(function(element) { /* ... */ })
map(function(element, index) { /* ... */ })
map(function(element, index, array){ /* ... */ })
map(function(element, index, array) { /* ... */ }, thisArg)

element Текущий обрабатываемый элемент массива.

index Индекс текущего обрабатываемого элемента в массиве.

Меня больше всего смущает пример использования map() для переформатирования объекта в массиве. На мой взгляд, дело запутанное из-за своих ключей, «ключ» и «значение». Если бы мы изменили kvArray на это,

const kvArray = [{ k: 1, v: 10 },
                 { k: 2, v: 20 },
                 { k: 3, v: 30 }];

const reformattedArray = kvArray.map(({ k, v}) => ({ [k]: v }));

, и это может работать хорошо. Вывод: [{'1': 10}, {'2': 20}, {'3': 30}].

Между фигурными скобками {k, v} значения двух ключей «k» и «v» присваиваются в новом формате, где значение «k» (например, 1) устанавливается как первый ключ в новый массив и значение «v» (например, 10) как значение «1».

Надеюсь, это поможет понять это, и я думаю… так оно и работает. Оригинальный код прикреплен ниже.

const kvArray = [{ key: 1, value: 10 },
                 { key: 2, value: 20 },
                 { key: 3, value: 30 }];

const reformattedArray = kvArray.map(({ key, value}) => ({ [key]: value }));

// reformattedArray is now [{1: 10}, {2: 20}, {3: 30}],

// kvArray is still:
// [{key: 1, value: 10},
//  {key: 2, value: 20},
//  {key: 3, value: 30}]

filter()

.filter() или Array.prototype.filter() — это интуитивно понятная функция, которая может фильтровать элементы из массива и возвращать их в виде нового массива. Во-первых, самый понятный способ использования filter() — это функция массива.

const newArray= originalArray.filter(itemInArray=>condition)

Возьмите простой пример, и это будет так:

// original array
const arr = [1,3,5,7,9]
// newArr is the new array
// a can be anything
// just like when you doing for ...in while programming Python script
// if a>3, a will be kept in the new array
const newArr = arr.filter(a=>a>3);
console.log(newArr);

Результат будет [ 5, 7, 9 ]. Будут сохранены только те элементы, которые прошли фильтр.

Синтаксис, скопированный из mdn, показан ниже.

// Arrow function
filter((element) => { /* ... */ } )
filter((element, index) => { /* ... */ } )
filter((element, index, array) => { /* ... */ } )
// Callback function
filter(callbackFn)
filter(callbackFn, thisArg)
// Inline callback function
filter(function(element) { /* ... */ })
filter(function(element, index) { /* ... */ })
filter(function(element, index, array){ /* ... */ })
filter(function(element, index, array) { /* ... */ }, thisArg)

reduce()

.reduce() или Array.prototype.reduce() эта функция вернет только один элемент в конце. .reduce() отличается от двух, упомянутых выше. Вместо того, чтобы возвращать массив, сокращение больше похоже на создание сводки введенной информации. Возьмем в качестве примера сумму массива:

const numbers = [1,2,3,4];
// calculate the sum and store it in sumOfNums
const sumOfNums = numbers.reduce((sum, num) =>sum + num);
console.log(sumOfNums);
// output: 10

sum берется как накопитель, при каждом вызове сумма плюс текущий элемент, num, и возвращаются значения обратно как новая сумма. Так же, как при выполнении цикла for:

sum+=num;

Синтаксис из mdn:

// Arrow function
reduce((previousValue, currentValue) => { /* ... */ } )
reduce((previousValue, currentValue, currentIndex) => { /* ... */ } )
reduce((previousValue, currentValue, currentIndex, array) => { /* ... */ } )

reduce((previousValue, currentValue) => { /* ... */ } , initialValue)
reduce((previousValue, currentValue, currentIndex) => { /* ... */ } , initialValue)
reduce((previousValue, currentValue, currentIndex, array) => { /* ... */ }, initialValue)

// Callback function
reduce(callbackFn)
reduce(callbackFn, initialValue)

// Inline callback function
reduce(function(previousValue, currentValue) { /* ... */ })
reduce(function(previousValue, currentValue, currentIndex) { /* ... */ })
reduce(function(previousValue, currentValue, currentIndex, array) { /* ... */ })

reduce(function(previousValue, currentValue) { /* ... */ }, initialValue)
reduce(function(previousValue, currentValue, currentIndex) { /* ... */ }, initialValue)
reduce(function(previousValue, currentValue, currentIndex, array) { /* ... */ }, initialValue)

Ссылка

MDN: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/Array

FreeCodeCamp: https://www.freecodecamp.org/learn/javascript-algorithms-and-data-structures/