TypeScript: разница между типами any и unknown

Вам наверняка известно, что TypeScript  —  это разновидность JavaScript.

Предполагаю, что вы знакомы с обоими этими языками. Тем не менее я начну с краткого введения в TypeScript.

Фактически TypeScript  —  это JavaScript с синтаксисом для типов. На W3Schools TypeScript определяют как синтаксическое надмножество JavaScript со статической типизацией. Это означает, что в TypeScript поверх JavaScript имеется синтаксис, что позволяет разработчикам добавлять типы.

Примитивы TypeScript

Вот основные примитивные типы TypeScript:

  • логический (булев)  —  значения true и false;
  • числовой  — целые числа и значения с плавающей точкой; строковый  —  заключенные в кавычки текстовые значения, например "TypeScript is Awesome";
  • any  —  с ним проверка типов отключается, фактически разрешаются все типы;
  • unknown  —  аналогичен any, но безопаснее;
  • never  —  когда он определяется, выбрасывается ошибка.

Описаний типов any и unknown явно недостаточно для их понимания. Это подводит нас к сути.

Разница между типами any и unknown

Вот два главных отличия any от unknown:

  1. В TypeScript, чтобы работать со значением unknown, необходимо определить его тип. С any этого делать не нужно.

Пример:

let anyValue: any = 1;
let unknownValue: unknown = 1;

anyValue.helloworld(); // Ошибки нет
unknownValue.helloWorld();  // получаем ошибку TypeScript

2. unknown присваивается самому себе или any, а any —  чему угодно.

Пример:

let anyValue: any = 1;
let unknownValue: unknown = 1;

let str: string;

str = anyValue; // Ошибки нет
str = unknownValue; // получаем ошибку TypeScript

Как видите, перед работой со значением unknown этими ограничениями гарантируется его проверка, что важно для снижения вероятности ошибок времени выполнения.

Варианты использования

1. Описание с помощью типа unknown неизвестного значения, например возвращаемого из сетевого вызова:

let data: unknown = getSomeValueFromSomeWhere();

if (typeof data === 'string') {
   //данные — строка.
} else if (Array.isArray(data)) {
   //данные — массив.
} else if (typeof data === 'object') {
   //данные — объект.
}

2. В утверждении типа

В TypeScript утверждение типа как способ информирования компилятора о типе переменной отличается от приведения типов тем, что код при этом не реконструируется. Утверждение типа применяется для указания типа значения, чтобы он не выводился компилятором.

Однако нельзя задать тип, который не совпадает с фактическим типом значения.

Пример:

let value = '1' as number; // Ошибка: нельзя сказать, что строка это число

interface Vehicle {
  name: string;
  model: string;
}

function buyVehicle(vehicle: Vehicle){}

buyVehicle({niceVehicle: ''} as Vehicle); // Ошибка: у этого объекта нет требуемых свойств интерфейса Vehicle.

Решение здесь заключается в том, чтобы задать значению unknown:

buyVehicle({niceVehicle: ''} as unknown as Vehicle)

Но этого решения следует избегать  —  с ним код становится небезопасным.

Заключение

Типы any и unknown —  это два полезных примитива TypeScript.

any может пригодиться для избежания ошибок, ведь проверка типов отключается. Но на TypeScript не обеспечивается типобезопасность, а инструменты, в которых используется связанная с типом информация, такие как автозаполнение, оказываются нерабочими.

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

P. S. any следует по возможности избегать.

Читайте также:

Читайте нас в TelegramVK и Дзен


Перевод статьи Joel Chi: TypeScript — Difference between ‘any’ and ‘unknown’ Types

Предыдущая статьяНастраиваем автоматизированную модерацию с помощью OpenAI
Следующая статья3 основных закона разработки ПО