9

看完这篇 MSDN 文章后,我现在想知道将集合定义为继承自ObservableCollection. 这之间是否有任何显着差异:

class MyCollection : ObservableCollection<MyObject> { }

class Class1
{
    private MyCollection _newCollection = new MyCollection();

    public Class1()
    {
        _newCollection.Add(new MyObject());
    }
}

还有这个:

class Class1
{
    private ObservableCollection<MyObject> _newCollection = new ObservableCollection<MyObject>();

    public Class1()
    {
        _newCollection.Add(new MyObject());
    }
}

有什么我在这里忽略的吗?

4

3 回答 3

11

一个主要的好处是您可以定义Add函数,这使得内联初始化更容易。所以例如这个:

class MyCollection : ObservableCollection<MyObject> 
{  
    public void Add(string prop1, string prop2)
    {
        base.Add(new MyObject { Prop1 = prop1, Prop2 = prop2 });
    }
}

让你写这个:

MyCollection collection = new MyCollection
{
    { "prop1", "prop2" },
    { "prop1", "prop2" },
};

第二个(相关的)好处:如果您正在使用 XAML,拥有一个子类集合可以让您将集合实例(用于设计/测试用例)定义为标记,如下所示:

<local:MyCollection xmlns:local="MyNamespace">
    <local:MyObject Prop1="prop1" Prop2="prop2" />
    <local:MyObject Prop1="prop1" Prop2="prop2" />
</local>

最后,(我想这只是一个口味问题)它一般不会受到伤害,并且可以提供帮助。有时,对于给定的集合类型,您最终需要更多的方法/属性。准备好一个类型化的子类,而不需要重构是很好的。

于 2013-07-26T00:05:06.810 回答
2

在您给出的示例中,没有特别的好处。一般来说,我认为公平地说,如果您不以某种方式扩展或覆盖继承的类,通常应该避免继承。话虽如此,您的样本对文章中的样本并不十分忠实。

public class NameList : ObservableCollection<PersonName>
{
     public NameList() : base()
        {
            Add(new PersonName("Willa", "Cather"));
            Add(new PersonName("Isak", "Dinesen"));
            Add(new PersonName("Victor", "Hugo"));
            Add(new PersonName("Jules", "Verne"));
        }
...

在 MSDN 示例中,他们在类构造函数中添加了额外的逻辑。在一个真实世界的例子中,这个类可能有一个构造函数,它采用某种存储库接口,或者从文件中读取,或者任何不属于 ObservableCollection 功能的东西所以你原来问题的答案是另一个问题“是否需要扩展 ObservableCollection<T>?”

于 2013-07-26T00:13:06.093 回答
2

该示例远非继承的良好用法,特别是对类几乎没有添加。

通常,当它提供有用的功能但您想要更多东西时,您可以考虑以与任何其他类相同的方式对其进行子类化。例如,您可能希望对插入采取特定操作、一些特殊处理、实现附加接口或一些不同的通知,然后根据需要继承和覆盖/添加成员。

一个实际的例子是在 WPF Caliburn.Micro的 MVVM 框架中完成的,它们BindableCollection<T>继承自ObservableCollection<T>,除了通知更改之外,它还执行线程 UI 编组。

于 2013-07-26T00:40:13.947 回答