使用新成员隐藏非虚拟成员的替代方法

本文关键字:方法 虚拟成员 新成员 隐藏 | 更新日期: 2023-09-27 18:36:35

假设我想做这样的事情:

class Foo
{
    public event BarHandler Bar;
    ...
}
class FooList<T> : List<T> where T : Foo
{
    public override void Add(T item)
    {
        item.Bar += Bar_Handler;
        base.Add(item);
    }
    private void Bar_Handler ...
    ...
}

但是Add List<T>不是虚拟的,所以我不能使用override,我将不得不求助于new。然而,这不提供多态性,我担心通过将FooList引用为简单的List可能会引入微妙的错误,这会导致我的事件处理程序不被添加。

我目前的具体情况是:我想为实现INotifyPropertyChanged的项目进行子类ObservableCollection,并在添加/删除这些项目时添加/删除事件处理程序。然后,我提供一个事件,如果集合中的任何项发生更改,则会引发该事件。

我想要一个针对我的特定问题以及潜在的一般问题的解决方案,因为这是我偶然发现的几次,来自 java 背景。

使用新成员隐藏非虚拟成员的替代方法

与其扩展List<T>,不如实现IList<T>接口并保存内部List<T>成员变量。这样,您就不会破坏现有的List<T>功能,并且仍然实现与List<T>相同的接口。

例:

class FooList<T> : IList<T> where T : Foo
{
    private List<T> m_internalList = new List<T>();
    public void Add(T item)
    {
        item.Bar += Bar_Handler;
        m_internalList.Add(item);
    }
    // other methods
}
List<T>

打算继承,因此Add方法不是虚拟的,但Collection<T>是虚拟的。您可以改为继承Collection<T>并重写InsertItem方法。

internal class MyCollection<T> : Collection<T> where T : Foo
{
    protected override void InsertItem(int index, T item)
    {
        item.Bar += Bar_Handler;
        base.InsertItem(index, item);
    }
}

相关:为什么不从List继承?

FWIW ObservableCollection<T>类本身继承Collection<T>