继承与组合:组合能有效解决依赖问题吗? [有效Java]

Inheritance vs Composition: Does composition effectively solve dependency issues? [Effective Java]

我对 Java 略有了解,在 Effective Java(2017) 中遇到了一些对我来说意义不大的东西。

下面是书中的一段。 (第 18 项)

Unlike method invocation, inheritance violates encapsulation. In other words, a subclass depends on the implementation details of its superclass for its proper function. The superclass's implementation may change from release to release, and if it does, the subclass may break, even though its code has not been touched. As a consequence, a subclass must evolve in tandem with its superclass, unless the superclass's authors have designed and documented it specifically for the purpose of being extended.

我理解在某些情况下组合可能比继承更受青睐,并且理解第 18 项的其他部分。但是,我发现很难理解组合方法如何防止上面段落中提到的问题(取决于实现细节) - 正如作者所说,正因为如此,组合比继承更好。在本章的后面,Bloch 给出了一个自定义 Set 实现的示例,他在其中使用 Forwarding Class(这显然取决于 Set 接口细节)。有人可能会争辩说 Set 接口不会经常更改,但实际上接口的更改也可能导致 Wrapper Class 中断(注意本书通过 Forwarding Class 和 Wrapper [=28 给出了一个示例=]).

我想如果 Bloch 意味着组合比继承相对安全是有道理的,因为 class 实现比接口更频繁地更改。但是,我认为Wrapper Class 和Interface 之间仍然存在依赖性问题,我很困惑为什么作者没有更清楚地说明这一点。

我是不是想错了?

(另外,不知道封装跟这个有什么关系,我对封装的理解就是用private隐藏变量..)

您实际上应该提供更多有关示例的信息,即“在本章的后面,Bloch 给出了自定义 Set 实现的示例”

基本上继承是子class会受到父class变化的影响。请参阅下面的代码:

public class Baby extends Human{

}

在上面的代码中,如果Human实现了另一个public或者protected方法,Baby会强制自动继承。相当严格。

但是对于组合来说,Owner 对象的变化并不需要子对象的变化,在一定程度上反之亦然。

public class Human{
  private Baby baby;
}

在上面的代码中,Human 可以有任何可能不会影响 Baby 的实现,反之亦然。在设计 Baby 和 Human 可以做什么方面有更多的余地。它们可以完全具有许多不同的属性和方法。

好的,所以我查看了@LeiYang 推荐的内容,然后意识到我的问题是无效的。给定的段落指出“子类取决于其超类的 实现细节 以实现其适当的功能” - Object Composition 没有问题,因为它仅按原样使用提供的方法(不覆盖)。因此 Object Composition 不违反封装,相对于 Inheritance.

相对稳定