Большая часть Фазы 1 буткемпа Flatiron Software Development была довольно гладкой (но в то же время веселой и сложной). Но по причинам, которые до сих пор мне неясны, метод .reduce() поставил меня в тупик дольше всего, намного. Я совершил ошибку, пройдя модули курса, не потратив времени на то, чтобы полностью их понять; затем, как только я наткнулся на задание, в котором меня просили создать метод .reduce() с нуля, мне пришлось вернуться и на самом деле копаться в том, чего я раньше не понимал. Промедление никогда не окупается!

Теперь, когда я, наконец, освоил метод .reduce(), объяснение его своими словами поможет закрепить его в моем сознании и, надеюсь, даст другим ясность, которая дается легче, чем мне.

Для начала давайте рассмотрим концепцию уменьшения массива значений и то, как мы можем закодировать это вручную.

const array = [1, 2, 3, 4];
let finalValue = 0;
function addArray(array) {
  for (const element of array) {
  finalValue += element;
  }
  return finalValue;
}
//Function call
addArray(array)
//=>10

Мы перебираем каждое значение в массиве для накопления и возврата одного значения. Эта конкретная функция просто складывает все элементы массива вместе, чтобы получить окончательную сумму.

Но что, если мы хотим сделать что-то более сложное с каждым элементом массива передсверткой? Нам придется написать другую функцию!

const array = [1, 2, 3, 4];
let finalValue = 0;
function multiplyAndAddArray(array) {
  for (const element of array) {
  finalValue += (element * 2);
  }
  return finalValue;
}
//Function call
multiplyAndAddArray(array)
//=>20

Одна концепция, которую я постоянно встречал на этапе 1, — это понятие «абстракции»: обобщенный код гораздо предпочтительнее статического кода/жесткого кодирования. Это экономит время и усилия, сводит к минимуму повторяемость, а также повышает удобство использования. Две приведенные выше функции подходят только для выполнения одной, конкретной операции с переданным массивом, и каждый раз необходимо писать весь цикл for!

Итак, давайте попробуем лучше придерживаться принципа обобщения и создадим функцию, которая уменьшает элементы массива в соответствии с функцией обратного вызова, переданной в качестве параметра. Это то, чем в конечном счете является .reduce(), встроенный метод в объект массива JavaScript.

Если бы мы создали .reduce() вручную, это выглядело бы примерно так:

function myReduce(array, callback, initialValue) { //will usually be 0, but can be any number
  //finalValue will be changed, but for now 
  //its value is the same as initialValue
  let finalValue = initialValue;
  //iterate through the passed-in array
  for (const element of array) {
    //vitally, the callback function is
    //invoked with finalValue, which changes with each iteration
    //thus "accumulating" it
    finalValue = callback(finalValue, element); 
  }
  return finalValue;
}
//A simple function used in myReduce() 
//that adds all elements of an array together
function addValues(finalValue, element) {
  return finalValue + element;
} 

//Function calls
myReduce([1, 2, 3, 4], addValues, 0)
//=>10
myReduce([1, 2, 3, 4], addValues, 10)
//=>20 (because we started with an initialValue of 10 rather than 0)

Вот более подробное описание того, что происходит с каждой итерацией массива [1, 2, 3, 4].

1st iteration:
  finalValue = 0
  element = array[0] = 1
  finalValue = 0 + 1 = 1

2nd iteration:
  finalValue = 1
  element = array[1] = 2
  finalValue = 1 + 2 = 3

3rd iteration:
  finalValue = 3
  element = array[2] = 3
  finalValue = 3 + 3 = 6

4th iteration:
  finalValue = 6
  element = array[3] = 4
  finalValue = 6 + 4 = 10

finalValue = 10

После всего вышеизложенного механика встроенного метода .reduce() (надеюсь) станет понятнее. Как и созданный вручную myReduce.(), он принимает функцию обратного вызова и начальное значение. Но встроенный метод уже присутствует во всех объектах Array, отсюда и отсутствие параметра массива в самой функции.

//General syntax
array.reduce(callback, initialValue)

//Practical example
[1, 2, 3, 4].reduce((initialValue, element) => initialValue + element, 0)
//=>10

//Make sure that initialValue is always the first parameter!

На этом я заканчиваю объяснение метода .reduce()! Даже во время написания этого мне приходилось консультироваться и пересматривать свою курсовую работу. Я уверен, что обращусь к этому посту хотя бы раз в обозримом будущем…

Я с нетерпением жду следующего этапа буткемпа Flatiron. Двенадцать недель назад я никогда в жизни не прикасался к JavaScript, а теперь успешно создал и развернул одностраничное веб-приложение с его использованием (плюс HTML и CSS)! Проверьте это ниже, если вам интересно!

Поиск рецептов коктейлей