generic Type(T)
与any
在 typescript 方面有何区别?
功能1
function identity(arg: any): any {
return arg;
}
功能2
function identity<T>(arg: T): T {
return arg;
}
功能3
function identity<T>(arg: T[]): T[] {
return arg;
}
如果我们传递任何类型的data type
,函数1和3都被接受,但是如果我们传递array
,函数2不接受。泛型类型在编译时接受所有类型的数据类型。但是为什么它不接受呢?
另外,哪个功能有助于提高性能(功能1或功能3)?
5条答案
按热度按时间lp0sw83n1#
如果这是只返回一个参数的恒等函数,并且没有类型限制,则没有区别:
类型化代码也有不同之处:
同样,泛型类型的使用提供了语义,这个签名暗示函数是无类型的,返回任何东西:
此签名表明函数返回的类型与其参数相同:
真实的函数通常比
return arg
示例更有意义,泛型类型可以受益于类型限制(而any
显然不能):但是,当函数与其他泛型类和泛型函数结合使用时(如果涉及非泛型,则会被消除),好处会变得更加明显:
这允许在输入(参数)和输出(返回值)之间一致地维护
T
类型:性能不会有任何差异,因为TypeScript类型仅存在于设计时。
suzh9iv82#
使用这些方法时绝对没有性能差异,因为所有这些花哨的东西都只是
Typescript
糖,只用于开发。所有的类型检查都只在编译时进行(在服务器中,当Typescript将您的代码转换回正常的javascript时)。
无论哪种方式,当您的代码被发送到用户的浏览器时,它看起来是这样的:
但为了解释差异:
当使用
any
时,您将丢失Typescript提供的所有类型检查和安全检查,而T
的行为就像一个变量,它将保存您不知道它将是什么的类型。所以
在上面,我们知道如果
identify
接受number
,它将返回number
,依此类推,其中:但是现在,您不知道
arg
和returned
值是否是同一类型。T
要解决的另一个问题是,当你在一个类中创建一个方法时,它需要一个参数,你要确保这个方法在示例化时,只接受与类的构造函数的参数类型相同的参数。因此,使用上述:
其中:
cedebl8k3#
T
的主要用途是避免在调用方法时中断类型。示例:
如果您这样做:
第二行对编译器来说是可以的,但不是因为他知道
bar
存在于Foo
类型中,而是因为它是any
,而any
可以有任何方法。如果您这样做:
第二行可以很好地编译,第三行不行,因为
Foo
没有notExistingMethod
方法。any通常用于需要以更类似于Javascript的方式创建内容的情况,这意味着您实际上并不知道对象中有什么,因为Javascript没有任何类型(我不是在谈论
es6
ofc)。h5qlskok4#
所有的东西在运行时都是
any
,在JavaScript
中编译时也是any
,这就是为什么有TypeScript
在编译时提供类型安全。any
与T
/T extends
等的区别在于,例如,在编译时具有类型安全如果函数接受了任何东西,那么在运行时就会出现错误,这就太晚了。
cigdeys35#
下面是一个简单的例子:
正如我们所知,
parseInt
在传入数组时将无法正常工作。在非泛型示例中,您只有在运行代码时才会注意到这一点。在泛型示例中,TypeScript将提前提醒您(这是类型安全的全部要点!)为什么一个抱怨,另一个不抱怨?
原因是泛型跟踪类型。这只适用于参数类型和返回类型相同的情况。否则就没有意义了。
何时应该使用泛型?
如果满足以下几点:
再举一个例子: