繁体   English   中英

`如何构造构造函数 <T> = Function&{prototype:T}`是否适用于TypeScript中的Abstract构造函数类型?

[英]How does `type Constructor<T> = Function & { prototype: T }` apply to Abstract constructor types in TypeScript?

关于TypeScript中的Abstract构造函数类型的问答,这是我想知道的答案:

TypeScript中的抽象构造函数类型

不幸的是,被接受的答案仅仅是一个无法解释的单行代码: type Constructor<T> = Function & { prototype: T }

看来,此答案对提问者来说已经足够了,它是公认的答案,但是我无法理解该答案如何应用于该问题。

我尝试在评论中提问,也尝试在聊天中询问某人以解释答案,但无济于事。 另外,我认识到这只是与那个问题几乎没有什么不同,但这仍然是关于代码的独特问题。

如何使用Function & { prototype: T }来模拟已知构造函数类型的抽象类?

JavaScript中 ,所有函数都有一个称为prototype的特殊属性。 如果将函数用作构造函数(通过new调用它),则构造的实例会将其作为原型。 这是ES2015之前的类在JavaScript中的工作方式:

// ES5-flavored class 
function Foo() { } // a normal function 
Foo.prototype.prop = 0; // adding a property to Foo.prototype
var f = new Foo(); // using Foo as a constructor
f.prop; // the instance inherits the added property

ES2015引入了class语法,该语法在幕后具有相同的行为...因此构造函数对象仍具有prototype属性,构造的实例从该属性继承。

// ES2015-flavored class
class Foo { } // explicitly a class
Foo.prototype.prop = 0; // adding a property to Foo.prototype
const f = new Foo(); // using Foo as a constructor
f.prop; // the instance inherits the added property

TypeScript通过声明所有函数实现的Function接口具有any类型prototype属性来对此建模。 此外,当class使用的语法,构造仍被视为一个Function ,和prototype的属性的构造是从变窄any相同类型的构造类实例:

// TypeScript code
class Foo { 
  prop!: number;  // Foo has a prop
} 
Foo.prototype; // inspects as type Foo
Foo.prototype.prop = 0; // so this works
const f = new Foo(); // inspects as type Foo
f.prop; // inspects as type number

即使TypeScript中的abstract类也具有prototype属性,其类型与实例类型相同。 因此,尽管您不能在抽象类构造函数上调用new ,也不能将其与new() => any类的可更新类型进行匹配,但仍然可以谈论其prototype

// more TS code
abstract class Bar {
  abstract prop: number;
}
Bar.prototype; // inspects as type Bar
Bar.prototype.prop = 0; // so this works
const b = new Bar(); // whoops can't do this though

所有这些都意味着在TypeScript中,可能抽象的类构造函数是Function (的子类型),其prototype属性是构造函数的实例类型。 因此,您可以说

type PossiblyAbstractConstructor<T> = Function & {prototype: T};

使用交集运算符将Function和“具有Tprototype属性的对象”组合起来...

或类似

interface PossiblyAbstractConstructor<T> extends Function {
  prototype: T;
}

使用接口扩展来达到相同的效果...

并且您知道以下内容有效:

const fooConstructor: PossiblyAbstractConstructor<Foo> = Foo;
const barConstructor: PossiblyAbstractConstructor<Bar> = Bar;

那应该解释原始问题的答案如何适用。 希望能有所帮助。 祝好运!

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM