TypeScript Academy · Урок

Типизированные утилиты pipe и flow

Создавайте конвейеры слева направо с точным выводом типов

Урок 4 из 413 шагов

«Типизированные утилиты pipe и flow» — бесплатный урок TypeScript Academy на CoddyKit. Это урок 4 из 4. Ты можешь прочитать весь урок бесплатно ниже — а потом практиковать его прямо в браузере с встроенным редактором кода и ИИ-репетитором 24/7. Это часть пути обучения TypeScript Academy, и твой прогресс синхронизируется между веб-версией и приложением CoddyKit. Курс TypeScript Academy содержит 4 уроков всего.

От compose к pipe

pipe передаёт значение через функции слева направо — в порядке чтения, который предпочитает большинство людей. pipe(x, f, g) означает g(f(x)).

Двухшаговый pipe

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

const pipe2 = <A, B>(a: A, f: (a: A) => B): B => f(a);
console.log(pipe2(5, n => n + 1)); // 6

Передача значения через несколько функций

pipe с тремя аргументами применяет функции последовательно. Выход каждого шага становится входом следующего.

function pipe<A, B, C>(a: A, f: (a: A) => B, g: (b: B) => C): C {
  return g(f(a));
}
const inc = (n: number) => n + 1;
const dbl = (n: number) => n * 2;
console.log(pipe(5, inc, dbl)); // 12

Чтение слева направо

В отличие от compose, pipe перечисляет шаги в порядке их выполнения. pipe(5, inc, dbl) сначала увеличивает значение, а затем удваивает его — именно так, как написано.

console.log(pipe(5, dbl, inc)); // 11 (double then inc)

Зачем нужны перегрузки

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

function pipe<A, B>(a: A, f: (a: A) => B): B;
function pipe<A, B, C>(a: A, f: (a: A) => B, g: (b: B) => C): C;
function pipe(a: unknown, ...fns: Function[]): unknown {
  return fns.reduce((v, fn) => fn(v), a);
}

Каждая перегрузка связывает типы

Перегрузка для двух функций связывает A -> B, а перегрузка для трёх — A -> B -> C. Компилятор выбирает подходящую перегрузку на основе количества переданных функций.

Реализация во время выполнения

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

function pipe(a: any, ...fns: Array<(x: any) => any>): any {
  return fns.reduce((acc, fn) => fn(acc), a);
}
console.log(pipe("  hi ", s => s.trim(), s => s.toUpperCase())); // HI

Изменение типов в pipe

Поскольку каждая перегрузка связывает обобщённые типы, pipe может преобразовать значение через несколько типов, сохраняя полную проверку типов.

const out = pipe("hello", s => s.length, n => n > 3);
console.log(out); // true (string -> number -> boolean)

flow: pipe без значения

flow похож на pipe, но принимает только функции и возвращает новую функцию. Значение можно передать позже, что особенно удобно для повторного использования.

const flow = <A, B, C>(f: (a: A) => B, g: (b: B) => C) =>
  (a: A): C => g(f(a));
const process = flow((n: number) => n + 1, (n: number) => n * 2);
console.log(process(5)); // 12

pipe против flow и compose

pipe применяет функции к значению слева направо; flow создаёт повторно используемую функцию слева направо; compose создаёт функцию справа налево. Выбирайте вариант с учётом порядка чтения и необходимости повторного использования.

Практические конвейеры

Библиотеки вроде fp-ts и Effect предоставляют надёжный, полностью типизированный pipe с множеством перегрузок. Создание небольшого собственного варианта помогает точно понять, как работает типизация.

Краткая проверка

Краткая проверка по этому уроку.

Итоги

pipe(x, f, g) = g(f(x)) выполняется слева направо и использует сигнатуры перегрузок для точной типизации каждого варианта по количеству аргументов, а реализация выполняется одной операцией reduce. flow — это вариант без явного значения, возвращающий повторно используемую функцию.

Можно начать бесплатно

Изучай TypeScript с ИИ-репетитором — бесплатно

Пиши и запускай код прямо в браузере, получай мгновенную помощь от ИИ-репетитора 24/7 и продолжи учиться на сайте или в приложении.

Курсы
101
Уроки
352

Часто задаваемые вопросы

Урок «Типизированные утилиты pipe и flow» бесплатный?

Да — полный текст урока «Типизированные утилиты pipe и flow» бесплатно доступен здесь в веб-версии. Чтобы практиковать его интерактивно (встроенный редактор кода и ИИ-репетитор 24/7) и разблокировать остальной курс TypeScript Academy, подпишись на CoddyKit PRO. Курс TypeScript Academy содержит 4 уроков всего.

Чему я научусь в уроке «Типизированные утилиты pipe и flow»?

Создавайте конвейеры слева направо с точным выводом типов Ты практикуешь TypeScript Academy с помощью реального кода, который запускаешь прямо в браузере, и ИИ-репетитор 24/7 отвечает на твои вопросы во время урока.

Нужен ли мне опыт, чтобы начать TypeScript Academy?

Предыдущий опыт не требуется. TypeScript Academy на CoddyKit структурирован для всех уровней — от новичков до продвинутых, поэтому ты можешь начать отсюда или с самого начала и учиться в своем темпе. Это урок 4 из 4.

Сколько времени занимает урок «Типизированные утилиты pipe и flow»?

Большинство уроков CoddyKit занимают около 5–10 минут. Каждый из них компактный и интерактивный, поэтому ты постоянно делаешь прогресс и продолжаешь с того же места в веб-версии и приложении.

Можно ли писать и запускать код в этом уроке TypeScript Academy?

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

Все уроки этого курса

  1. Чистые функции и неизменяемость
  2. Каррирование и частичное применение
  3. Композиция функций с типами
  4. Типизированные утилиты pipe и flow
← Назад к TypeScript Academy