【问题标题】:Why does TypeScript not raise a warning when an interface is overridden为什么在覆盖接口时 TypeScript 不会发出警告
【发布时间】:2014-06-11 20:53:30
【问题描述】:
interface ClockInterface {
    setTime(d: Date);
}

class Clock implements ClockInterface  {
    // I would expect this to raise a compile error 
    // as it's not implementing the interface
    setTime(d) {
        // some logic that needs an instance of Date
    }
}

var cc = new Clock();

// otherwise it allows you to do any bad stuff you want.
cc.setTime(234);
cc.setTime('234');
cc.setTime([]);

当然,将setTime(d) { 更改为setTime(d: Date) { 确实会导致对setTime 的最后3 次调用引发警告。

一个更简单的例子就是:

class Clock implements ClockInterface  {
    setTime() {
        // some logic that needs an instance of Date
    }
}

【问题讨论】:

    标签: typescript


    【解决方案1】:

    Liskov Substitution Principle。该类可替代接口,所以它可以implement它。

    当你说implements 时,TypeScript 执行的唯一检查是“类是否可以分配给指定的接口?”。考虑这种情况:

    interface CatVeterinarian {
        checkup(a: Cat): void;
    }
    
    interface HumanDoctor {
        checkup(a: Human): void;
    }
    
    class UniversalDoctor implements CatVeterinarian, HumanDoctor {
        checkup(a: Animal) {
            // ...
        }
    }
    

    假设这是一个错误:你将如何解决它?你的UniversalDoctor 类真的可以同时充当CatVeterinarianHumanDoctor。你无事可做。

    您可以使用非Date 参数调用Clock 这一事实仅仅代表了一个额外 功能——接受任意setTime 参数的能力。显然,编译器说“你的类太多,它不满足那个接口*;几乎每个接口的实现者都会有一些额外的'东西'不属于原始界面。

    【讨论】:

    • 好吧,那我误解了接口的用途。如果您将一个类声明为实现它们,它们的目的是什么,而它们会立即完全忽略接口? (顺便说一句,我认为只要HumanCat 扩展Animal,您的示例就不会出错,但是如果您已将UniversalDoctor 检查为:checkup(a: Rock) {...checkup() {...checkup(a: any) {...CatVeterinarian 检查是checkup(a: Cat, owner: Human): void; 我希望UniversalDoctor 检查出错(否则声明一个类实现接口有什么意义?)
    • 在您列出的预期错误的情况下,这将是一个错误。
    • (1 / 2) TypeScript 是一种结构化类型系统;所有空接口都可以互换。不要使用空接口进行尝试,因为很多东西在应该出错的时候不会出错。
    • (2 / 2) UniversalDoctor.checkup 有 0 个参数意味着它将实现任何具有相同返回类型的函数。这里的一般规则是“您可以忽略参数以进行子类型化”(这对于像 Array#forEach 这样的东西是必需的,您传递的回调没有来声明它可能的每个参数不想)
    • “不要使用空接口来尝试事情”非常好,已经编辑了那个要点和第二个例子现在(正确)错误。而且我更了解接口,我只是希望他们能做更多。感谢您如此积极响应和乐于助人!
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2023-04-08
    • 2015-08-13
    • 1970-01-01
    • 1970-01-01
    • 2021-08-19
    • 2017-04-09
    相关资源
    最近更新 更多