在TS中,相信很多人搞不清Object
,object
以及{}
之间的关系,或者没有深究过,觉得他们只是同一个类型的不同别名,其实不然,每一个的存在都是有原因的。今天我们一起来探究他们的不同之处。
{}
包含了除了null
跟undefined
所有的类型,类似于这样:
image.png
(这也是{}
跟unknown
的区别,unknown
可以包含null
跟undefined
)
但是它对它所指向的对象一无所知,访问任何属性或者方法都会报找不到:
image.png
{}
就像一个大集合,包含了其他的类型。
{}
其实整个类型系统都是如此,类型表示值的集合。在我们日常coding过程中,时不时会遇到Argument of type 'xxx' is not assignable to parameter of type 'xxx'.
的报错,其实就是看我们要赋的值在不在我们声明的对象的集合里面。(比如"foo"|"bar"
这种literal type
可以赋给接受string
类型的变量)。
类似于{}
,所有拥有Object
原型的值都能赋给Object
作为类型的变量。
image.png
但是有一丢丢规则,值的原型里得有Object
(当然了,JS的大部分值都是有的)。
Object1.png
它所指向的对象一无所知,访问任何属性或者方法都会报找不到:
image.png
需要注意,Object
对于对象里的某些方法是有要求的(比如Object
原型对象的toString
方法):
image.png
这里Object
就不能用了,而{}
没有这种检查。这种行为有时候让人迷惑,所以二者选其一,我选{}
,😁
然后就是object
类型了。
object
跟{}
有一点不同,它不包含原始类型。
object.png
除了这一点,其它的跟{}
很相似。
image.png
一般情况下,我们应该一个也不用😝。如果我们知道我们数据的具体结构,那单独创建一个type
或者interface
是最好的。但是在类型编程的时候,我们就得选一个。
比如我们有一个merge
函数,用来合并两个对象,把我们可能会这么写:
function merge<A extends {},B extends {}>(a:A,b:B):A&B{
return {
...a,
...b
}
}
或者这样:
function merge<A extends Object,B extends Object>(a:A,b:B):A&B{
return {
...a,
...b
}
}
看起来没问题,但我们传给它原始类型它是可以接受的,结果似乎有点奇怪:
image.png
这大概不是我们写merge
函数想要的效果。如果这时候我们把类型参数换成object
,问题就迎刃而解了。
image.png
所以:
object
{}
null
跟undefined
的情况,用unknown
扫码关注腾讯云开发者
领取腾讯云代金券
Copyright © 2013 - 2025 Tencent Cloud. All Rights Reserved. 腾讯云 版权所有
深圳市腾讯计算机系统有限公司 ICP备案/许可证号:粤B2-20090059 深公网安备号 44030502008569
腾讯云计算(北京)有限责任公司 京ICP证150476号 | 京ICP备11018762号 | 京公网安备号11010802020287
Copyright © 2013 - 2025 Tencent Cloud.
All Rights Reserved. 腾讯云 版权所有