Разница между type и interface в TypeScript
В TS есть два способа описать структуру данных - type и interface.
На первый взгляд они похожи: оба позволяют объявлять объекты, описывать сигнатуры функций и имплементацию классов.
Но есть важные отличия, которые стоит понимать.
В современном TS типы и интерфейсы практически взаимозаменяемые. Но тип может использоваться для примитивов, а интерфейс нет (всегда объектный тип).
В простых случаях интерфейс и тип почти одно и то же (скрин 1).
И TUser, и IUser описывают одинаковую структуру объекта.
Чтобы объединить несколько типов: для интерфейсов используется extends, а для типов - пересечение (&).
При этом TypeScript рекомендует использовать интерфейсы. Почему так?
Есть несколько причин.
1️⃣ Производительность и проверки типов:
TypeScript кэширует отношение интерфейсов внутри компилятора, что делает компиляцию более эффективной.
А вот пересечения типов каждый раз пересчитываются заново.
Из-за этого скорость проверки типов выше, особенно в больших и сложных типах.
2️⃣Как TypeScript проверяет совместимость.
Когда мы сравниваем объект с типом A & B - TS сначала проверяет совместимость с A, потом с B
При interface extends - TS работает с единым структурным описанием типа.
3️⃣Отсюда третий момент - ошибки.
У интерфейсов ошибки обычно короче и понятнее: TS сразу показывает все конфликтующие поля.
Через type - вычисляет пошагово и сначала сообщит, что не хватает одного ключа, а уже потом другого.
В примере (скрин 2) ошибка при использования type, говорит, что отсутствует поле agе, но не говорит про поле address, которое тоже отсутствует.
4️⃣Интерфейсы поддерживают объединение объявлений (declaration merging).
Если объявить интерфейс с тем же именем, что и уже существующий, TS объединит их свойства.
Это может показаться небезопасным.
Однако у этого есть важный плюс: часто необходимо расширять уже существующие интерфейсы, например:
- Добавлять новые свойства к браузерным событиям.
- Расширять глобальные объекты, например Window, если внешняя SDK добавляет на него свой инстанс класса (скрин 3).
В таких случаях declaration merging позволяет TS понимать новые свойства и типизация при этом остается корректной. С type так делать нельзя.
Я в проектах предпочитаю везде использовать интерфейсы, а типы только для примитивов.
✈️ Telegram | 🎓 Менторство | 📹 YouTube | 👩💻 Roadmap
Post #101
2.35K



- 🔥 28
- 👍 9
- ✍ 7
- ❤ 5
- 😁 1
- 🤣 1