Главная Категории Контакты Поиск

Функции высшего порядка (HOF) в JavaScript

Что такое функции высшего порядка (HOF) в JavaScript и как их использовать.

JavaScriptFunctional programming·16.05.2019·читать 2 мин 🤓·Автор: Alexey Myzgin

Функции высшего порядка (higher order functions) в JavaScript - необходимый строительный блок функционального программирования на любом языке.

Функция более высокого порядка выполняет по крайней мере одну (чаще обе) из следующих вещей:

  • принимает функцию в качестве аргумента;
  • возвращает новую функцию.

Чтобы продемонстрировать это, мы создадим функцию более высокого порядка, withCount(), которая модифицирует любую переданную ей функцию, и выводит в консоль информацию о том, сколько раз она была вызвана, а также аргументы args с которыми она была вызвана.

const withCount = fn => {
  let count = 0;

  return (...args) => {
    console.log("calling with", args);
    console.log(`Call count: ${++count}`);
    const result = fn(...args);
    console.log("called with", args, ", returned", result);
    return result;
  };
};

withCount принимает любую переданную ей функцию fn в качестве аргумента. Она будет, выводить в консоль информацию о том, сколько раз мы вызывали нашу новую переданную ей функцию, а также аргументы args. Для этого мы создаем переменную count с изначальным значением 0. Далее мы возвращаем новую функцию, которая использует оператор rest для сбора, переданных ей аргументов. Внутри тела нашей функции возврата, мы выводим в консоль значение count, перед этим увеличивая его. И возвращаем результат функции, которая была вызвана с оператор spread переданных ей аргументов.

Теперь, когда у нас есть функция высшего порядка - withCount, давай создадим простую функцию add для использования и передадим эту функцию ей. Функция add получит x и y в качестве аргументов и вернет их суммирование. Теперь мы можем создать функцию countedAdd, используя нашу функцию withCount, передав ей add.

const withCount = fn => {
  let count = 0;

  return (...args) => {
    console.log("calling with", args);
    console.log(`Call count: ${++count}`);
    const result = fn(...args);
    console.log("called with", args, ", returned", result);
    return result;
  };
};

const add = (x, y) => x + y;

const countedAdd = withCount(add);

Теперь давай выйдем в консоль нескольких вариантов использования countedAdd, с разными аргументами.

const withCount = fn => {
  let count = 0;

  return (...args) => {
    console.log("calling with", args);
    console.log(`Call count: ${++count}`);
    const result = fn(...args);
    console.log("called with", args, ", returned", result);
    return result;
  };
};
const add = (x, y) => x + y;

const countedAdd = withCount(add);

console.log(countedAdd(1, 2));
console.log(countedAdd(2, 2));
console.log(countedAdd(3, 2));

Если мы запустим это, то увидим в консоле количество вызовов для каждого из них, а также аргументы args с которыми они были вызваны и результат.

calling with [1, 2]
Call count: 1
called with [1, 2] , returned 3
3

calling with [2, 2]
Call count: 2
called with [2, 2] , returned 4
4

calling with [3, 2]
Call count: 3
called with [3, 2] , returned 5
5

Website, name & logo
Copyright © 2022. Alex Myzgin