Typescript抽象类静态方法没有强制执行

prm*_*mph 1 static abstract-class static-typing interface typescript

我在TypeScript中有这个简单的代码:

abstract class Config {
    readonly NAME: string;
    readonly TITLE: string;

    static CoreInterface: () => any
}

class Test implements Config {
    readonly NAME: string;
    readonly TITLE: string;
}
Run Code Online (Sandbox Code Playgroud)

即使Test类中缺少CoreInterface()成员,TypeScript也不会抱怨.为什么是这样?

我需要每个派生类在CoreInterface()静态函数中提供有关自身的一些元数据.我知道我可以扩展Config类并让每个子类提供自己的CoreInterface()实现,但我不希望子类自动继承COnfig类的任何成员.这就是为什么我使用"implements"而不是"extends"

Nit*_*mer 9

根据您的评论,以下是您如何实现您的目标:

interface ConfigConstructor {
    CoreInterface: () => any;
    new (): Config;
}

interface Config {
    readonly NAME: string;
    readonly TITLE: string;
}

const Test: ConfigConstructor = class Test implements Config {
    readonly NAME: string;
    readonly TITLE: string;

    static CoreInterface = function (): any { return "something"; }
}
Run Code Online (Sandbox Code Playgroud)

(游乐场代码)

如果你注释掉其中一个成员(即:),NAME你会收到这个错误:

类'Test'错误地实现了接口'Config'.
"测试"类型中缺少属性"NAME".

如果您注释掉静态,CoreInterface您将收到此错误:

类型'typeof Test'不能分配给'ConfigConstructor'类型.
'typeof Test'类型中缺少属性'CoreInterface'.


原始答案

静态成员/方法不能用于继承(一般来说对OO都是如此,而不是特定于typescript)因为(如@JBNizet所评论的)所有静态属性都属于类本身而不属于实例.

正如维基百科文章所述:

即使尚未存在该类的实例,也可以调用静态方法.静态方法称为"静态",因为它们在编译时根据调用它们的类进行解析,而不是像实例方法那样动态解析,实例方法根据对象的运行时类型进行多态解析.因此,无法覆盖静态方法

还要检查一下这个帖子:为什么静态方法不被认为是好的OO练习?

至于你想要实现的目标,在扩展类时不能实现静态方法的编译错误,但是你可能会遇到运行时错误:

class A {
    static fn() {
        throw new Error("not implemented!");
    }
}

class B extends A {
    static fn() {
        console.log("B.fn");
    }
}

class C extends A { }

B.fn(); // ok
C.fn(); // error: not implemented!
Run Code Online (Sandbox Code Playgroud)

(游乐场代码)

  • 检查我修改后的答案 (2认同)