我正在阅读打字稿中的interfaces,碰到了以下内容。
名为Square
的接口定义如下:
interface Square {
width: number
}
然后通过将类型为literat的对象类型转换为square
类型来声明名为Square
的变量:
let square = <Square>{}
我尝试打印square
和typeof square
,它们按预期给出了{}
和object
。但是我无法将以上square
的定义与以下内容区分开来:
let sq: Square = {}
此处的打字稿引发错误,表明width
中缺少属性sq
。这与上面的强制转换语法有何不同?这也是snippet from typescript-playground。
答案 0 :(得分:5)
类型断言强制编译器接受不安全类型的内容。因此,当您使用类型断言时,编译器将接受{}
是Square
,即使它显然不符合接口。
当您显式注释变量时,let sq: Square
的类型由注释确定,并且将严格根据该变量类型检查赋值,并且会收到错误消息,表明{}
不符合界面。
从运行时的角度来看,两者之间没有区别,在两种情况下,编译后剩下的就是将{}
分配给变量,类型(在注解和类型断言中)将被完全擦除。编译器。
通常,您应该避免类型断言。类型断言告诉编译器:“忽略程序员认为更好的东西!”。在某些情况下,必须使用类型断言,但是除非您确定需要使用类型断言,否则应避免使用它们,并尝试解决问题以使类型正确。使用类型断言,您可能会得到令人惊讶的结果。例如:
interface Square {
width: number
}
let square = <Square>{}
square.width.toExponential() // runtime error, the type did not really reflect the runtime object
let sq:Square = {} // error here at compile time here
sq.width.toExponential()