【问题标题】:Overriding private methods in typescript重写打字稿中的私有方法
【发布时间】:2021-10-19 17:58:44
【问题描述】:

注意这个带有公共方法message() 的版本可以编译并且greet() 可以按预期工作,

class Foo {
    public greet() {
        console.log(`Hello, ${this.getMessage()}`);
    }
    getMessage() : string {
        return "I am Foo"
    }
}

class Goo extends Foo {
    getMessage() : string {
        return "I am Goo";
    }
}

getMessage() 标记为私有,Goo 类不再编译:

class Foo {
    public greet() {
        console.log(`Hello, ${this.getMessage()}`);
    }
    private getMessage() : string {
        return "I am Foo"
    }
}

class Goo extends Foo {
    private getMessage() : string {
        return "I am Goo";
    }
}

我经常使用私有方法来分解较大的方法,方法是抽象出低级代码块以提高可读性,正如许多关于该主题的书籍所推荐的那样,我将它们设为私有,因为它们不打算被类的使用者调用,但由于某种原因,当需要为我的基类的某些子类修改这些较低级别的方法之一时,打字稿对我不利。

实际上,除了必须在扩展类中实现公共方法之外,还有其他方法可以做到这一点,或者通过将支持方法的“脏衣服”包含在基类的公共接口和子类?

另外,我想知道打字稿作者的动机是什么,因为这个看似任意的规则是公共方法可以被覆盖但私有方法不能被覆盖?

【问题讨论】:

  • 将其标记为受保护而不是私有。私有方法对扩展类是不可见的,受保护的方法是。这就是 C# 的实现方式,打字稿主要反映了 C#

标签: typescript


【解决方案1】:

正如 bryan60 所说,使用 protected 修饰符:

class Foo {
  public greet() {
    console.log(`Hello, ${this.getMessage()}`);
  }

  protected getMessage(): string {
    return "I am Foo";
  }
}

class Goo extends Foo {
  protected getMessage(): string {
    return "I am Goo";
  }
}

const goo = new Goo();
goo.greet(); // Hello, I am Goo

来自the handbook

protected 修饰符的作用与 private 修饰符非常相似,但声明为 protected 的成员也可以在派生类中访问。

例如:

// Property 'getMessage' is protected and only accessible within class 'Goo'
// and its subclasses.
goo.getMessage();

class Hoo extends Goo {
  public getMessage(): string {
    return "I am Hoo";
  }

  public tryToGetGoosMessage(goo: Goo): string {
    // Property 'getMessage' is protected and only accessible through an
    // instance of class 'Hoo'.
    return goo.getMessage();
  }

  public doOtherHoosHoo(hoo: Hoo) {
    // ok, this is inside Hoo
    hoo.hoo();
  }

  protected hoo() {}
}

const hoo = new Hoo();
// ok, getMessage is public in Hoo
hoo.getMessage();

// Class 'Joo' incorrectly extends base class 'Hoo'.
//  Property 'getMessage' is protected in type 'Joo' but public in type 'Hoo'.
class Joo extends Hoo {
  protected getMessage(): string {
    return "I am Joo";
  }
}

Playground link

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2017-02-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-04-03
    • 2018-03-04
    相关资源
    最近更新 更多