Почему TypeScript рассматривает каждый номер своего собственного типа?

Выражение 1==2 заставляет TypeScript выдавать ошибку Operator '==' cannot be applied to types '1' and '2'. Каковы причины того, что TypeScript обрабатывает эти значения как разные типы (оператор typeof, скорее предсказуемо, говорит, что они оба number s)? Является ли проектным решением специально применять это к числам или побочным продуктом общей системы набора текста? Какой вред может быть вызван сравнением литералов?

Ответ 1

1 и 2 в этом контексте считаются так называемыми буквальными числами. Это означает, что значение 1 имеет тип 1 и, следовательно, может быть только 1, то же самое с 2. Учитывая, что выражение 1==2 не имеет смысла, потому что 1 никогда не может быть 2, или, точнее, их несоответствие типов, вы не можете сравнивать яблоки с апельсинами.

Вот обоснование и подробные сведения о том, где по умолчанию используются типы литералов:

О буквальных типах:

Один из многих примеров того, зачем нужны литералы:

Ответ 2

Когда TypeScript выводит вывод типа в выражении 1, он дает ему тип 1, а не тип number. Вы можете увидеть это, если вы исследуете код следующим образом:

const a = 1;

Если вы используете вашу IDE для запроса выводимого типа a, вы увидите, что тип a 1. Например, на TypeScript игровая площадка вы получаете подсказку с надписью const a: 1.

Итак, в if (1 == 2), 1 имеет тип 1, а 2 имеет тип 2. TypeScript не позволяет сравнивать их, потому что они имеют разные предполагаемые типы. Это часть безопасности типа TypeScript.

Вы можете обойти это с помощью:

if (1 as number == 2) {
}

И вы упомянули в комментарии, что вы проводили сравнение 1 == 2, потому что вы не могли сделать if (false) { ... } из-за компилятора, жалующегося на недостижимый код. Я могу решить эту проблему следующим образом:

if (false as boolean) {
    console.log("something");
}

Ответ 3

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

function doStuff(p : "yes"| 1| true| "no"| 0| false ){

}

doStuff("maybe"); //Error
doStuff(3); // Error
doStuff(1) ; //OK

Вы испытываете неудачный побочный эффект, что ошибки, такие как ваши, вместо отчетов как expression is always false, вместо этого превращаются в ошибки совместимости типов.