赞成inheritance遗产
喜欢inheritance的构成
是非常stream行的词组。 我读了几篇文章,最后每篇文章都说
当类之间存在纯粹的IS-A关系时使用inheritance。
这篇文章的一个例子:
这里苹果和水果之间有明确的IS-A关系,即苹果IS-A水果,但作者也表明,苹果HAS-A水果(成分),以显示inheritance实施时的陷阱。
我在这里变得有些困惑,这个陈述的含义是什么
当类之间存在纯粹的IS-A关系时使用inheritance。
使用构成而不是inheritance是否意味着即使存在纯粹的IS-A关系,也总是尝试应用构图,而仅仅在构图没有意义的情况下才留下inheritance?
当使用inheritance重用超类的代码,而不是重写方法并定义另一个多态行为时,通常表示应该使用组合而不是inheritance。
java.util.Properties
类是inheritance性不好的一个很好的例子。 它并没有使用 Hashtable来存储它的属性,而是扩展了 Hashtable,以便重用它的方法并避免使用委托来重新实现它们。
我认为这是面向对象devise中讨论最多的一点。 正如文章中所build议的,构图总是比inheritance更受欢迎。 这并不意味着你不应该使用inheritance。 你应该在哪里更有意义(这可以辩论)。
使用构图有很多优点,其中有两个是:
- 你将完全控制你的实现。 即,您只能公开您打算公开的方法。
- 超类中的任何更改都可以通过仅在您的类中进行修改来屏蔽。 任何使用你的类的客户端类,都不需要修改。
- 允许您控制何时加载超类(延迟加载)
在这篇文章中,没有这样一句话:
use inheritance when there is pure IS-A relationship between classes
而且,除了你的post外,谷歌没有在其他地方find它。
相反,文章写道:
Make sure inheritance models the is-a relationship. My main guiding philosophy is that inheritance should be used only when a subclass is-a superclass. In the example above, an Apple likely is-a Fruit, so I would be inclined to use inheritance.
这意味着,如果存在IS_A关系,则首先尝试使用inheritance,而不是组合。 并没有偏好using composition over inheritance
– 每个都有利于自己的angular色。
另外,我想补充一点, Decorator模式是一个例子,你可以使用inheritance的组合,并dynamic地向对象添加责任。 有效的Java中的“赞成组合inheritance”项中提到了装饰器模式的示例。 以Java API为例, BufferedReader装饰一个阅读器(而不是扩展FileReader,PipedReader,FilterReader等),因此有能力装饰任何types的阅读器。 缓冲function是在运行时附加到这些阅读器,这是装饰者模式。
这里通过子类扩展是不切实际的。
我想一个好的指导方针是:
当存在IS-A关系时,使用inheritance。 否则,使用组合。
其原因与面向对象devise中的另一个概念 – 多态。 多态性是许多OOP语言的一个特性,其中一个对象可以用来代替另一个对象,只要第一个类的类是第二个类的子类。
为了说明,想象一下,如果你有一个function,接受一种动物。 当你使用inheritance时,你只有一个函数:
void feed( Animal a );
多态性向我们保证,我们放入的任何动物的子类都将被接受。 否则,我们将被迫为每种types写一个函数。 我认为这样做的好处大于弊(如减less封装)。
如果没有IS-A关系,我认为多态性不会很有效。 因此使用组合并且增强类之间的封装/隔离会更好。
当关系是永久的时候使用inheritance。 不要使用扩展只是为了获得自由的行为。 这就是他们提到的IS-A例子。 只有扩展类真正是父类的扩展才能扩展。 有些时候它不会被切割干燥,但总的来说。 如果您需要从“正确”的课程延伸,作文也提供了未来的灵活性。
这是一个古老而又伟大的文章:
http://www.javaworld.com/javaworld/jw-08-2003/jw-0801-toolbox.html
我会说不。 在水果/苹果的情况下,使用inheritance是很有意义的。 这篇文章的作者也证实了这一点:“在上面的例子中,苹果可能是一个水果,所以我会倾向于使用inheritance”。
如果你的子类显然是一个超类,inheritance是好的。 实际上,你会发现更多的情况,使用组合更好的解决。