TypeScript中如何为泛型类定义别名实现复用并正确实例化?
问题原因说明
你遇到的报错是TypeScript的类型擦除机制导致的:type关键字定义的类型别名仅存在于编译阶段,运行时会被完全删除,自然无法作为构造函数执行new操作。
和C++模板实例化会生成真实运行时类的逻辑不同,TypeScript的所有类型定义都不会参与最终运行时代码的生成,你定义的FooNumber只是一个类型标注,不是真实存在的运行时值。
对应实现方案
TypeScript中可以通过以下两种常用方式实现类似C++模板别名的复用效果:
方案1:定义指定泛型的子类
直接继承原泛型类并指定泛型参数,生成的子类是运行时真实存在的构造函数,可以直接实例化:
class Foo<T> { // 类原有逻辑 } class FooNumber extends Foo<number> {} class FooString extends Foo<string> {} // 可以正常实例化 const numIns = new FooNumber(); const strIns = new FooString();
方案2:绑定构造函数类型到原类
如果你不想额外生成子类,也可以将指定了泛型的构造函数类型绑定到原类的值上:
class Foo<T> { // 类原有逻辑 } // 先定义带泛型的构造函数类型 type FooNumberConstructor = new () => Foo<number>; // 将类型绑定到原类的值上 const FooNumber = Foo as FooNumberConstructor; // 也可以正常实例化 const numIns = new FooNumber();
与C++ decltype对应的能力
TypeScript中与C++ decltype 作用接近的是类型上下文下的typeof操作符,它可以提取某个值的TypeScript类型,示例如下:
const demo = new Foo<number>(); // 提取demo的类型,等价于Foo<number> type DemoType = typeof demo;
注意区分两种typeof:在类型标注、泛型参数等类型上下文中使用的typeof是TS提供的类型查询能力,仅在编译阶段生效;在普通代码逻辑中使用的typeof是JavaScript原生能力,返回运行时的类型字符串。
内容的提问来源于stack exchange,提问作者HelloWorld
相关产品推荐
相关产品推荐

