Защита типов TypeScript

Защита типа — это мощная функция TypeScript, которая позволяет разработчикам выполнять проверки во время выполнения, чтобы сузить тип переменной. Это обеспечивает более точную информацию о типе, что приводит к более безопасному и предсказуемому коду. В этой статье рассматривается, что такое защита типа и как ее эффективно использовать.

Что такое защитные приспособления?

Типовые защитные функции — это выражения, которые выполняют проверки во время выполнения и позволяют TypeScript выводить более конкретный тип для переменной. Они помогают различать разные типы, особенно при работе с типами union. Типовые защитные функции могут быть реализованы с использованием различных методов, включая:

  • Предикаты типа, определяемые пользователем
  • Утверждения типа
  • Проверки экземпляров
  • Использование оператора typeof
  • Использование оператора in

Предикаты типа, определяемые пользователем

Предикаты типа, определяемые пользователем, — это функции, которые возвращают логическое значение и имеют специальный тип возвращаемого значения, который указывает тип проверяемой переменной. Вот как их создавать и использовать:

function isString(value: any): value is string {
  return typeof value === 'string';
}

function printString(value: any) {
  if (isString(value)) {
    console.log(value.toUpperCase()); // TypeScript knows value is a string here
  } else {
    console.log('Not a string');
  }
}

В приведенном выше примере isString — это определяемый пользователем предикат типа, который помогает TypeScript понять, что value — это строка внутри блока if.

Утверждения типа

Утверждения типа сообщают TypeScript, что переменную следует рассматривать как определенный тип. Этот метод не выполняет проверку во время выполнения, но информирует компилятор TypeScript о типе. Например:

function printLength(value: any) {
  console.log((value as string).length); // Assert value is a string
}

В этом примере value as string сообщает TypeScript, что value — это строка, без выполнения проверки во время выполнения.

Проверки экземпляров

Проверки экземпляров используются для определения, является ли объект экземпляром определенного класса. Это полезно для сужения типов при работе с классами:

class Dog {
  bark() { console.log('Woof'); }
}

class Cat {
  meow() { console.log('Meow'); }
}

function speak(animal: Dog | Cat) {
  if (animal instanceof Dog) {
    animal.bark(); // TypeScript knows animal is a Dog here
  } else {
    animal.meow(); // TypeScript knows animal is a Cat here
  }
}

В этом примере оператор instanceof помогает TypeScript вывести тип animal на основе его класса.

Использование оператора typeof

Оператор typeof можно использовать для проверки примитивных типов, таких как string, number и boolean:

function processValue(value: string | number) {
  if (typeof value === 'string') {
    console.log(value.toUpperCase()); // TypeScript knows value is a string here
  } else {
    console.log(value.toFixed(2)); // TypeScript knows value is a number here
  }
}

Здесь typeof используется для проверки того, является ли valuestring или number, и соответствующим образом сужает тип.

Использование оператора in

Оператор in проверяет наличие свойства в объекте. Это полезно для различения типов, которые имеют общие свойства:

interface Bird {
  fly: () => void;
}

interface Fish {
  swim: () => void;
}

function move(creature: Bird | Fish) {
  if ('fly' in creature) {
    creature.fly(); // TypeScript knows creature is a Bird here
  } else {
    creature.swim(); // TypeScript knows creature is a Fish here
  }
}

В этом примере оператор in помогает TypeScript определить, является ли creatureBird или Fish, на основе наличия метода.

Заключение

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