TypeScript предлагает два способа работы с типами:
- Явное задание типа: Вы явно указываете тип переменной.
- Автоматическое выведение типа: TypeScript автоматически определяет тип на основании присвоенного значения.
Когда использовать каждый подход:
- Явное определение типов: Используйте явное определение типов для аргументов функций, типов возврата, литералов объектов и случаев, когда начальное значение может отличаться от конечного типа.
- Автоматический вывод типа: Используйте автоматический вывод типа для простых объявлений переменных с немедленным присваиванием, когда тип очевиден из контекста.
Явные аннотации типов
Явное объявление типа означает, что вы явно говорите TypeScript, каким именно должен быть тип переменной:
Базовые явные типы
// Строка
let greeting: string = "Привет, TypeScript!";
// Число
let userCount: number = 42;
// Булевый тип
let isLoading: boolean = true;
// Массив чисел
let scores: number[] = [100, 95, 98];
Функция с явными типами
// Функция с явными параметрами и типом возврата
function greet(name: string): string {
return `Привет, ${name}!`;
}
// TypeScript проверит, что аргумент имеет верный тип
greet("Алиса"); // ОК
greet(42); // Ошибка: Аргумент типа '42' не может быть назначен параметру типа 'string'.
Автоматический вывод типов
TypeScript может автоматически определять (выводить) тип переменной на основе её первоначального значения:
Автоматический вывод базовых типов
// TypeScript выводит тип 'string'
let username = "alice";
// TypeScript выводит тип 'number'
let score = 100;
// TypeScript выводит тип 'boolean[]'
let flags = [true, false, true];
// TypeScript выводит тип возврата как 'number'
function add(a: number, b: number) {
return a + b;
}
any, если вы в своём файле конфигурации tsconfig.json не включили опцию strictNullChecks.
Когда автоматический вывод типа эффективен
Автоматический вывод типов литералов объекта
// TypeScript выводит структуру объекта
const user = {
name: "Алиса",
age: 30,
isAdmin: true
};
// TypeScript знает, что эти свойства существуют
console.log(user.name); // ОК
console.log(user.email); // Ошибка: Свойства 'email' не существует
Типобезопасность в действии
Одна из главных преимуществ TypeScript — выявление ошибок, связанных с типами, на этапе разработки.
Рассмотрим, как TypeScript предотвращает частые ошибки.
Ошибки несоответствия типов
// Явное несоответствие типов
let username: string = "alice";
username = 42; // Ошибка: Тип 'number' не может быть назначен типу 'string'
// Неявное несоответствие типов
let score = 100; // TypeScript выводит 'number'
score = "high"; // Ошибка: Тип 'string' не может быть назначен типу 'number'
JavaScript против TypeScript
В JavaScript следующий код был бы абсолютно корректным, несмотря на то, что он может привести к неожиданным результатам:
Поведение в JavaScript
// Это допустимый в JavaScript код, но может вызывать ошибки
function add(a, b) {
return a + b;
}
console.log(add("5", 3)); // Возвращает "53" (конкатенация строк)
TypeScript выявляет подобные проблемы ещё на этапе компиляции:
Безопасность типизации в Typescript
function add(a: number, b: number): number {
return a + b;
}
console.log(add("5", 3)); // Ошибка: Аргумент типа 'string' не может быть назначен параметру типа 'number'
Когда TypeScript не может автоматически вывести тип
Хотя автоматический вывод типа в TypeScript весьма силён, бывают случаи, когда не получается однозначно определить тип. Тогда TypeScript возвращается к типу any, отключающему проверку типов.
any и другие специальные типы TypeScript подробно рассматриваются в следующей главе.
Распространённые случаи, когда появляется тип any
// 1. JSON.parse возвращает тип any, так как структура данных неизвестна на этапе компиляции
const data = JSON.parse('{ "name": "Alice", "age": 30 }');
// 2. Переменные, объявленные без инициализации
let something; // Тип 'any'
something = 'привет';
something = 42; // Нет ошибки
Избегайте any, когда это возможно
Использование типа any отключает проверку типов TypeScript.
Вместо этого рассмотрите следующие альтернативы:
- Используйте аннотации типов.
- Создавайте интерфейсы для сложных объектов.
- Используйте защитные конструкции типов для проверки типов во время выполнения.
- Включите опцию
noImplicitAnyв вашем файлеtsconfig.json.