TypeScript Academy · Урок

Сложение и вычитание на уровне типов

Создавайте арифметические операции с помощью преобразования кортежей

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

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

Арифметика с помощью длины

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

type BuildTuple<N extends number, Acc extends unknown[] = []> =
  Acc["length"] extends N ? Acc : BuildTuple<N, [...Acc, unknown]>;

Сложение

Чтобы сложить A + B, постройте кортеж длины A, затем кортеж длины B, объедините оба в новый кортеж и считайте его длину.

type Add<A extends number, B extends number> =
  [...BuildTuple<A>, ...BuildTuple<B>]["length"];

type S = Add<3, 4>; // 7

Почему объединение даёт сложение

Кортеж длины 3, за которым следует кортеж длины 4, образует кортеж длины 7. Объединение отметок двух счётных таблиц даёт общую таблицу, поэтому длины складываются.

type A = Add<2, 2>; // 4
type B = Add<0, 5>; // 5
type C = Add<1, 6>; // 7

Вычитание с помощью префикса

Чтобы вычислить A - B, постройте кортеж длины A, а затем выведите его как префикс длины B, за которым следует остаток. Длина rest равна A - B.

type Sub<A extends number, B extends number> =
  BuildTuple<A> extends [...BuildTuple<B>, ...infer Rest]
    ? Rest["length"]
    : never;

type D = Sub<7, 4>; // 3

Пошаговое вычитание

Для Sub<7, 4> постройте кортеж длины 7, сопоставьте ему префикс длины 4, получите Rest длины 3 и считайте его длину. Удалённый префикс содержит ровно B отметок.

type A = Sub<5, 2>; // 3
type B = Sub<4, 4>; // 0

При выходе за нижнюю границу возвращается пустой тип

Числа на уровне типов здесь неотрицательны. Если B > A, допустимого префикса не существует, шаблон не срабатывает, а результатом становится never. При желании можно задать для него значение по умолчанию 0.

type A = Sub<2, 5>; // never

type SubSafe<A extends number, B extends number> =
  [Sub<A, B>] extends [never] ? 0 : Sub<A, B>;
type B = SubSafe<2, 5>; // 0

Увеличение и уменьшение

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

type Inc<N extends number> = [...BuildTuple<N>, unknown]["length"];
type Dec<N extends number> =
  BuildTuple<N> extends [unknown, ...infer R] ? R["length"] : 0;

type A = Inc<4>; // 5
type B = Dec<4>; // 3

Умножение повторением

Умножение — это многократное сложение. Добавляйте B к аккумулятору A раз, уменьшая счётчик с помощью Dec и накапливая результат с помощью Add.

type Mul<A extends number, B extends number, Acc extends number = 0> =
  A extends 0 ? Acc : Mul<Dec<A>, B, Add<Acc, B>>;

type A = Mul<3, 4>; // 12

Вспомогательный тип BuildTuple

Каждая описанная здесь операция зависит от BuildTuple. Это единственный переиспользуемый примитив: передайте ему число и получите кортеж такой длины. Держите его в одном месте, а остальные операции стройте поверх него.

type Five = BuildTuple<5>; // [unknown, unknown, unknown, unknown, unknown]
type N = Five["length"];   // 5

Композиция операций

Поскольку каждая операция принимает число и возвращает число, их можно свободно комбинировать. Можно записывать выражения вроде Add<Mul<2, 3>, 4>, и компилятор вычислит их.

type Result = Add<Mul<2, 3>, 4>; // 10

Практическая осторожность

Эти приёмы отлично подходят для небольших количеств: индексов массивов, фиксированных размеров и ограниченных диапазонов. Для больших чисел или общей математики они непрактичны из-за ограничения рекурсии и отсутствия отрицательных чисел. Используйте их там, где значения остаются небольшими и статичными.

type A = Add<8, 7>;  // 15 (fine)
// Add<5000, 5000> would exceed recursion limits

Быстрая проверка

Проверьте, насколько хорошо Вы поняли арифметику на уровне типов.

Итоги

Вы реализовали арифметику в системе типов.

  • Сложение: объединить кортежи и считать длину.
  • Вычитание: вывести префикс и считать длину остатка.
  • Inc/Dec — варианты выполнения одного шага.
  • BuildTuple — общий примитив.

Далее: сравнение чисел на уровне типов.

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

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

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

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

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

Урок «Сложение и вычитание на уровне типов» бесплатный?

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

Чему я научусь в уроке «Сложение и вычитание на уровне типов»?

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

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

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

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

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

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

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

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

  1. Подсчёт с помощью длины кортежа
  2. Сложение и вычитание на уровне типов
  3. Сравнения на уровне типов
  4. Практические утилиты числовых типов
← Назад к TypeScript Academy