【问题标题】:The benefits of Composite Pattern over simple inheritance复合模式相对于简单继承的好处
【发布时间】:2011-03-17 09:34:40
【问题描述】:

我试图弄清楚为什么复合比简单继承更好。

例如,假设我们要实现一个文件系统。 所以基本上我们需要文件和文件夹。 我们可以使用复合模式,而FileFolder 类继承基接口,Folder 类持有接口类型集合。

但看起来(无论如何对我来说)简单的继承可以做同样的事情。 如果File 是根类并且Folder 继承自File,则Folder 可以保存Files 的集合,故事结束。

我错过了什么吗?

【问题讨论】:

  • 答案在某种程度上取决于所使用的语言。您对哪种语言或一组语言感兴趣?
  • 在某些语言中没有多重继承。您的建议剥夺了您从 File 以外的任何东西继承 Folder 某些功能的机会。
  • 目前我使用的是c#(或java)

标签: design-patterns


【解决方案1】:

如果File是根类,Folder继承File,则Folder可以存放Files的集合

这本质上是复合模式,即使你不这样称呼它:-)

除了在您的变体中,Folder 将继承它不能(或更糟:不应该)使用的特定于文件的功能。因此,您最终会使实施复杂化,以确保例如客户端不能将字节附加到文件夹的“末尾”等。

仅供参考,GoF 书籍Pattern Hatching 的续集,讨论了使用各种模式(包括 Composite)实现文件系统。强烈推荐阅读。

【讨论】:

  • 我问这个是因为我在工作面试中进行了测试。我没有使用复合模式。我做了一个简单的继承,因为该文件没有任何东西可以从文件夹类中隐藏。我确信这就是我没有通过的原因,我的应用程序按照他们的要求运行。感谢您的链接!
  • @Avi,在一般的类设计中不建议从具体类继承;这几乎总是为微妙的身份/比较问题和错误打开大门。例如。考虑到要比较的另一个对象实际上可以是Folder,你会怎么写File.compareTo()
  • 老实说,在您的示例中,我看不出简单继承和复合之间的区别。在这两种情况下,文件和文件夹都不是同一类型。
  • @Avi,不同之处在于,在经典的 Composite 中,层次结构的基础是接口或抽象类(我们称之为 Node),由文件夹和文件实现。因此,后者将是真正不同的类型,与您的设计相反,文件夹 是一个 文件。
【解决方案2】:

一个重要的区别在您的示例中变得很明显。在大多数语言中,继承是一种编译时机制。您在源代码中定义类的关系。

组合通常与继承结合使用(更确切地说是polymorphism)。如果部件具有多态接口,您可以在运行时决定如何组合复杂对象。

最后,这取决于所使用的语言。在 C++ 中,继承只能用于多态性和never for code-reuse。在像 Python 这样的语言中,这是不正确的。在这里,您可以通过组合和继承实现相同的目标。

【讨论】:

    【解决方案3】:

    我向您推荐 Head First Design Patterns 这本书,名为 Intro to Design Patterns 的第一章讨论了策略模式,并且有一个非常详细的示例,您可以自己了解组合以及为什么我们更喜欢组合而不是继承。

    【讨论】:

      【解决方案4】:

      我会建议你更好地阅读这个 pdf:--http://userpages.umbc.edu/~tarr/dp/lectures/Composite-2pp.pdf 这个 pdf 肯定会帮助你。谢谢。

      【讨论】:

      • PDF 链接已损坏
      猜你喜欢
      • 2014-10-13
      • 2011-02-17
      • 2012-01-30
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2013-05-15
      • 1970-01-01
      • 2010-11-25
      相关资源
      最近更新 更多