我有一个像这样的超类:
public abstract class Foo {
//some method here
public void aMethod() {
//some code
}
}
以及扩展BarOne
类的2个子类BarTwo
和Foo
。
在BarOne
中,一切正常,但在BarTwo
中,我想要@Deprecated
aMethod()
准确地说:我的意思是隐藏它,而不是因为隐私原因而弃用。有没有更好的方法而不是覆盖方法?
答案 0 :(得分:7)
即使从技术上来说可能,它在概念上也是错误的。因为这是违反Liskov替代原则的概念。
你知道,继承不仅仅是在你的源代码中放置A extends B
。我们的想法是基类中的方法定义了一个契约。使用这些方法的代码不需要关注关于这样的方法在基类中实现 - 或在子类中重写的事实。
您基本上是这样说的:我希望在基类上使用方法x()
,但我想表示在子类上不推荐使用x()
。这意味着调用x()
的代码只应该在基类实例上调用方法时才这样做。
因此,这里的非答案是:甚至不要考虑做那样的事情。在所有继承级别上,某个方法“可以被调用”,或者不是。没有必要仅对儿童班级施加这种限制。
所以真正的答案在这里:退一步,并考虑为什么你想出了这个想法。然后寻找其他方法来解决这个问题。
鉴于关于隐藏的评论:同样的故事。从技术上讲:你不能隐藏一个方法。因为,正如调用foo.bar()
是某个基类foo
实例的有效语句时所说的那样 - 当foo
碰巧是子类的实例时,它也需要是一个有效的语句。
唯一合法的是:
答案 1 :(得分:5)
你正在描述这样的事情:
___________
| class Foo |
| |
| aMethod() |
|___________|
/ \
/ \
_________/____ __\___________
| class BarOne | | class BarTwo |
| | | |
| inherits | | hides |
| aMethod() | | aMethod() |
|______________| |______________|
你不能也不应该这样做,正如GhostCats回答中所述。
然而,你可以做的是这样的事情:
___________
| class Baz |
| |
|___________|
/ \
/ \
_________/____ __\___________
| class Foo | | class BarTwo |
| | | |
| aMethod() | |______________|
|______________|
|
|
______|_______
| class BarOne |
| |
| inherits |
| aMethod() |
|______________|
然后 Baz
将拥有Foo
以前拥有的所有代码,aMethod()
除外。 Foo
只会添加aMethod()
并成为所有类的超类,希望继承aMethod()
,Baz
是所有类的超类,它们不想继承aMethod()
。