【问题标题】:Java: protected method in interfaceJava:接口中的受保护方法
【发布时间】:2013-04-07 23:10:30
【问题描述】:

好的,我知道这个问题已被问过几次,但我需要针对我的具体案例的建议。有 Encodable 和 Decodable 之分,Message 既是 Encodable 又是 Decodable:

interface Encodable { void encode(); }
interface Decodable { void decode(); }
class Message implements Encodable, Decodable { ... }

void processEncodable(Encodable encodable) {
  ...
  encodable.encode();
  ...
}

除了Message之外还有其他的Encodable(和Decodable),需要在processEncodable中处理。到目前为止一切都很好,但问题是我想从包外部隐藏 encode() 和 decode() ,并且 Java 接口不允许受保护/私有方法。有人可能会建议抽象类,但正如您所见,Message 应该同时继承 Encodable 和 Decodable,所以情况并非如此。有什么建议?

这些天我非常喜欢 Scala,Scala 特征允许受保护/私有方法,恕我直言,这更直观。我已经阅读了一些提到 Java 接口设计理念的答案,但我真的不明白为什么如果引入接口作为多重继承的替代方案,它为什么不应该允许受保护的方法,而抽象类则允许......

【问题讨论】:

  • 为什么您认为您的案例的答案与您已经提到的您已阅读的答案不同? stackoverflow.com/questions/5376970/protected-in-interfaces
  • 没错。不要尝试以非设计方式使用接口。
  • @atk:因为那里的答案对我没有太大帮助。它只说“Java就是这样”。另外,是的,“接口应该意味着您可以从类外部看到的内容”,但为什么不在类外部而仅在包内部,就像抽象类支持一样?
  • 我认为问题必须是让Encodable.encode() 返回Encodable 是否是个好主意。仅当您想对某些内容进行两次编码时,这才有意义。如果Encodable.encode() 返回一个Decodable 和Decodable.decode() 一个Encodable,这不是更有意义吗?至少我会期望一些被编码的东西是可解码的。

标签: java oop access-modifiers


【解决方案1】:

作为替代品并不意味着它是完全替代品。接口是服务契约,因此它们将某个类提供给其客户端的功能公开,作为任何可以访问该接口的客户端。

如果您想从包外部隐藏encode 和decode(这意味着您的逻辑也应该保留在带有Message 类的包中)不要通过接口公开它们,而是,允许它们成为您的Message 类(或超类,如果各种类可编码/可解码)的protected(或包私有)方法。 p>

这不是一个孤立的规则。有一些机制可以在不破坏接口概念的情况下实现你想要的。想一想:如果您只能在包中访问该方法,那么该方法对接口有什么好处?如果这些方法可以是类方法,并且通过适当的修饰符也可供包的成员使用,那么在接口中包含这些方法有什么意义?

【讨论】:

  • 我试图概括设计,从而尽可能地重用代码。有各种可编码的类,所以我想避免将 encode() 放在 Message 中。而且消息需要既可编码又可解码,因此超类也不是一种选择,因为不允许多重继承。
  • @KJ 我不明白为什么你的超类不能是Encodable 并且同时具有编码/解码方法。是否存在类可编码但不可解码或反之亦然的情况?这对我来说没有多大意义,但如果这是你的情况,你可以使用 UnsupportedOperationException 或标志来指示这种行为。
  • 确切地说,可编码对象不一定可解码,反之亦然。消息只是它们相交的一种特殊情况。编码操作与解码操作不同,如果可能的话,我想将它们分成不同的模块。
  • @KJ 确实编码和解码是不同的操作,但是为什么一个对象应该是可编码的而不是可解码的呢?它们将来会被解码还是由第三方解码?它们不能永远保持编码。我只是想了解您的上下文,以便我们提出最佳选择。我认为这里的问题也涉及到一些设计领域。
猜你喜欢
  • 2013-09-02
  • 2016-07-25
  • 1970-01-01
  • 2011-07-19
  • 2010-11-17
  • 2010-09-30
  • 2011-08-04
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多