JS: Функции
Теория: Отображение (map)
Рассмотрим следующую задачу. Возьмём список пользователей и извлечём из него имена всех пользователей:
Здесь мы видим обычную агрегацию с использованием цикла for...of. А что, если нам понадобится извлечь возраст? Повторяем:
В примерах выше легко увидеть закономерность. Выполняется один и тот же проход по циклу, и результат собирается в массив result. Единственное, что меняется — значение, которое мы извлекаем из элементов исходного массива.
Операция, которую мы выполняли в обеих ситуациях, называется отображением (mapping). В коде мы взяли исходный массив и отобразили его в другой массив, попутно выполнив необходимые преобразования над каждым элементом. Важно, что размер получившегося массива равен размеру исходного массива.
Задача отображать данные в реальном коде встречается буквально на каждом шагу. Это настолько важная операция, что для нее создана специальная функция высшего порядка map():
Метод map() принимает первым параметром функцию. Дальше, внутри себя, map() перебирает элементы переданной коллекции и для каждого элемента вызывает переданную функцию. На вход этой функции передаётся элемент исходного массива, а её результат записывается в новый массив, который и возвращается наружу.
Сравните решение задачи получения списка имен через цикл и с помощью метода map(). Последний имеет довольно много преимуществ. Во-первых, код с ним значительно короче. Во-вторых, от нас скрыта повторяющаяся логика перебора. Больше не нужно явно определять цикл и выполнять руками все те операции, которые можно не выполнять. Метод map() позволяет сосредоточиться на сути происходящего, скрывая ненужные детали (проход по циклу).
Типичный пример, который любят приводить в документации к функции map() разных языков программирования — применение некоторой арифметической операции к каждому элементу коллекции:
Пример выглядит искусственно, но хорошо отражает суть операции.
Реализация
Напишем свою собственную функцию myMap(), работающую аналогично методу массива map():
Главное отличие кода функции myMap() (и метода map()) от ручного обхода массива заключается в том, что функция myMap() не знает, что нужно сделать с каждым элементом массива. Поэтому она принимает вторым аргументом функцию, которую вызывает для каждого элемента исходного массива, а результат вызова записывается в выходной массив. Чем будет этот результат — функция myMap() не знает, и ей этого знать не нужно. Ответственность за обработку лежит на пользователях.




