Type Assertion
TypeScript дозволяє вам будь-яким способом перевизначати його виведене та проаналізоване представлення типів. Це робиться за допомогою механізму під назвою "type assertion"(затвердження типу). Затвердження типу TypeScript полягає в тому, що ви просто повідомляєте компілятору, що ви знаєте про типи краще, ніж він сам, і що він не повинен здогадуватися про вас.
Загальним випадком використання підтвердження типу є перенесення коду з JavaScript на TypeScript. Для прикладу розглянемо такий шаблон:
Тут помилки коду, оскільки визначений тип foo
є {}
, тобто об’єкт із нульовими властивостями. Тому вам не дозволяється додавати до нього bar
або bas
. Ви можете виправити це просто за допомогою твердження типу as Foo
:
as foo
vs. <foo>
as foo
vs. <foo>
Спочатку було додано синтаксис <foo>
. Це показано нижче:
Однак існує неоднозначність у граматиці мови під час використання тверджень стилю <foo>
в JSX:
Тому тепер для узгодженості рекомендується використовувати просто as foo
.
Type Assertion vs. Casting
Причина, чому це не називається "приведенням типів", полягає в тому, що casting зазвичай передбачає певну підтримку часу виконання. Однак type assertions — це суто конструкція під час компіляції та спосіб для вас надати підказки компілятору щодо того, як ви хочете, щоб ваш код аналізувався.
Assertion considered harmful
У багатьох випадках твердження дозволить вам легко перенести застарілий код (і навіть скопіювати та вставити інші зразки коду у свою кодову базу). Однак ви повинні бути обережними з використанням тверджень. Візьміть наш оригінальний код як зразок, компілятор не захистить вас від того, щоб ви забули фактично додати властивості, які ви обіцяли:
Ще одна поширена думка полягає в тому, що твердження використовують як засіб автодоповнення, наприклад:
але небезпека тут та сама, якщо ви забудете властивість, компілятор не скаржиться. Краще, якщо ви зробите наступне:
У деяких випадках вам може знадобитися створити тимчасову змінну, але принаймні ви не будете давати (можливо, помилкових) обіцянок, а натомість покладатиметеся на висновок типу, щоб перевірити за вас.
Double assertion
Затвердження типу, незважаючи на те, що воно дещо небезпечне, як ми показали, не є повністю відкритим. наприклад наступне є дуже дійсним випадком використання (наприклад, користувач вважає, що передана подія буде більш конкретним випадком події), а твердження типу працює, як очікувалося:
Однак наступне, швидше за все, є помилкою, і TypeScript скаржиться, як показано, незважаючи на твердження користувача про тип:
Якщо ви все ще бажаєте цей тип, ви можете використати подвійне твердження, але спочатку стверджуючи unknown
(або any
), який сумісний з усіма типами, і тому компілятор більше не скаржиться:
How TypeScript determines if a single assertion is not enough
Загалом, твердження від типу S
до T
є успішним, якщо або S
є підтипом T
, або T
є підтипом S
. Це робиться для забезпечення додаткової безпеки під час виконання тверджень типу ... абсолютно дикі твердження можуть бути дуже небезпечними, і вам потрібно використовувати unknown
(або any
), щоб бути такими небезпечними.
as any as
vs as unknown as
as any as
vs as unknown as
Обидва equally unsafe з точки зору TypeScript. Використовуйте те, що робить вас щасливими. Міркування:
Лінтери віддають перевагу
unknown
(з правиломno-explicit-any
)any
— це менше символів для введення, ніжunknown
Last updated