An alternative to hiding non-virtual members with new ones
Suppose I want to do something like this:
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 ...
...
}
But Add
in is List<T>
not virtual, so I cannot use override
, I have to resort to new
. This does not provide polymorphism, however, and I am worried about subtle bugs that can be introduced by referencing FooList
as simple List
that would result in my event handler not being added.
My current specific case is this: I want to subclass ObservableCollection
for elements that implement INotifyPropertyChanged
, and add / remove an event handler for those elements if added / removed. Then I provide an event that fires if any item in the collection changes.
I would like to find a solution for my specific problem as well as the main general problem as this somehow stumbled upon the java background several times.
source to share
Instead of extending, List<T>
you can implement an interface IList<T>
and keep an internal member variable List<T>
. This way you don't break existing functionality List<T>
and still implement the same interface as List<T>
.
Example:
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
}
source to share
List<T>
is not intended to be inherited and hence the method is Add
not virtual, but Collection<T>
. Instead, you can inherit Collection<T>
and override the method 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);
}
}
Related: Why not inherit from list <T>?
FWIW ObservableCollection<T>
class itself inherits Collection<T>
.
source to share