TypeScript中===与Object.is()类型校验差异及错误信息疑问
===与Object.is()的类型检查差异及错误信息疑问解答 嘿,这个问题抓得很准,我来一步步帮你理清:
一、为什么===会报错,Object.is()却不会?
首先得明确TypeScript 2.0引入的**字面量类型(Literal Types)**特性:false、true、"string"、1这些具体的值,在TS里会被当作独立的字面量类型,而不仅仅是boolean、string、number的子类型。
- 对于
===运算符,TS的类型检查会做严格的类型一致性校验:当你写if (false === true)时,左边的类型是false字面量,右边是true字面量,这是两个完全不同的类型,TS会认为这种比较是无意义的(编译阶段就能确定结果是false,且类型不匹配),所以抛出错误。 - 而
Object.is()的类型定义是Object.is(value1: any, value2: any): boolean,它的参数被声明为any类型,意味着TS会跳过对这两个参数的严格类型检查,允许你传入任意类型的值,自然不会触发报错,它的行为更贴近原生JS的运行时逻辑。
二、错误信息是否有误?
你提到的错误信息"operator '===' cannot be applied to types 'false' and 'true'"其实是准确的,并非表述错误:
这里的false和true指的是字面量类型,而不是宽泛的boolean类型。比如你如果定义两个变量:
const a: false = false; const b: true = true; if (a === b) {} // 同样会触发相同的错误
因为a的类型被明确为false,b的类型是true,二者是完全独立的字面量类型,所以TS会精准提示类型不匹配,而不是笼统的boolean类型。
三、新版本TypeScript是否修复?
首先要说明:这并不是TS的bug,而是它的严格类型检查设计特性。在后续的TS版本中(包括最新版本),这个行为仍然被保留——只要是两个不同的字面量类型用===比较,依然会触发类似的错误提示,因为TS认为这种编译期就能确定无意义的比较应该被拦截。
不过如果是使用宽泛的基础类型(比如boolean、string、number)的变量进行比较,就不会报错:
const x: boolean = false; const y: boolean = true; if (x === y) {} // 不会报错,因为x和y的类型是boolean(包含true和false的联合类型)
而Object.is()的类型定义在新版本中也没有本质变化,依然允许传入任意类型的参数,所以始终不会触发这类类型错误。
你提到的字符串、数字场景也是同样的逻辑:"string"和"string1"是不同的字符串字面量类型,1和2是不同的数字字面量类型,所以===比较会报错,而Object.is()因为参数是any类型,不会触发检查。
内容的提问来源于stack exchange,提问作者Ramesh Rajendran

