使用组合优于继承的优点是我们需要向List添加行为<>?

时间:2010-04-06 17:45:54

标签: inheritance oop composition

在此示例中,选项2优于1的优点/缺点是什么?

选项1(继承):

public class SalesList : List<Sales>
{
    //methods that add extra behavior List<Sales>
}

选项2(组成):

public class SalesList 
{
    private List<Sales> _list;
    //methods that add extra behavior to List<Sales>
}

5 个答案:

答案 0 :(得分:2)

选项2的优点是敏捷性。使用组合,您可以选择公开的列表界面的哪些部分。

想象一下,稍后您决定不再从另一个类扩展。到目前为止,您库中的一些用户将使用List提供的方法,因此您需要自己实现所有列表方法:add / addAll / contains / retainAll。这是为简单的销售清单实施的大量方法。

基本上,这归结为Joshua Bloch在Bumper-Sticker API Design中谈到的“当有疑问时,将其遗漏”。 API的每个方面都应尽可能小,但不能小一些。您可以随时添加内容,但不能将其删除。

答案 1 :(得分:2)

Composition的主要缺点是,如果需要提供相同的接口,则需要包装(复制)私有List的所有公共方法,在继承中,所有这些方法都已经可用,但是您无法覆盖其中任何一个都不能覆盖(在C#中它意味着该方法应该标记为'virtual',在Java中它不能被标记为'final')。

在C#3及更高版本中,您可以使用扩展方法,它可以在不真正弄乱层次结构树的情况下提供继承的外观。

答案 2 :(得分:2)

继承允许我们形成类的层次结构,这样父类就是* super *集,并且它的所有子元素都是* sub * set,这允许泛化,专业化并应用substitution principle

答案 3 :(得分:1)

选项1
  - 优点 - 继承的所有优点&amp;再利用
  - 缺点 - 代码现在向消费者发出信号,表明它是从列表中删除的。如果需要在以后更改,那么所有相关的消费者都将受到影响。

选项2
  - 优点 - 销售数据存储的实施细节从消费者中抽象出来。因此,如果实现需要更改(例如,例如字典),该类的使用者将免于这些更改。
  - 缺点 - SalesList类现在需要公开其他方法来获取和/或设置内部_list对象。这是需要维护的附加代码。此外,如果内部实现发生变化,您需要注意仍然支持以前的行为......

只是想到了一些想法。

HTH。

答案 4 :(得分:0)

在组合中,您可以在运行时动态更改超类实现。 但是使用继承,您无法在运行时更改超类实现。

在合成中,它取决于您传递给setter的对象类型,它将基于此行为。它将为实施提供更大的灵活性