WithEvents LinkedList是不可能的?

时间:2010-03-05 10:50:11

标签: .net vb.net collections

WithEvents Collection - VB.NET的最佳方法是什么?

您对下面的代码(跳过Nothing验证)有任何评论吗?

问题是当我在LinkedListNode(Of Foo)块中获得For Each时我可以设置 myNode.Value = something,这是处理程序泄漏......

- 在这种情况下,我可以覆盖FooCollection的GetEnumerator吗? -没有。 :(导致 NotInheritable Class LinkedListNode(Of T)

Class Foo
  Public Event SelectedChanged As EventHandler
End Class

Class FooCollection
  Inherits LinkedList(Of Foo)
  Public Event SelectedChanged As EventHandler

  Protected Overloads Sub AddFirst(ByVal item As Foo)
    AddHandler item.SelectedChanged, AddressOf OnSelectedChanged
    MyBase.AddFirst(item)
  End Sub

  Protected Overloads Sub AddLast(ByVal item As Foo)
    AddHandler item.SelectedChanged, AddressOf OnSelectedChanged
    MyBase.AddLast(item)
  End Sub

  ' ------------------- '

  Protected Overloads Sub RemoveFirst()
    RemoveHandler MyBase.First.Value.SelectedChanged, _
                         AddressOf OnSelectedChanged
    MyBase.RemoveFirst()
  End Sub

  Protected Overloads Sub RemoveLast(ByVal item As Foo)
    RemoveHandler MyBase.Last.Value.SelectedChanged, _
                        AddressOf OnSelectedChanged
    MyBase.RemoveLast()
  End Sub

  ' ------------------- '

  Protected Sub OnSelectedChanged(ByVal sender As Object, ByVal e As EventArgs)
    RaiseEvent SelectedChanged(sender, e)
  End Sub
End Class

3 个答案:

答案 0 :(得分:1)

主要问题是您无法正确覆盖GetEnumerator函数。在这种情况下,我会创建一个不直接从LinkedList继承但只使用一个作为私有字段的类:

Class FooCollection
    Implements ICollection(Of Foo)

    Private list As New LinkedList(Of Foo)

    Public Sub AddFirst(ByVal item As Foo)
        AddHandler item.SelectedChanged, AddressOf OnSelectedChanged
        list.AddFisrt(item)
    End Sub

    ...

End Class

它需要更多的编码,因为你需要实现所有的功能,而不仅仅是你想要覆盖的功能,但实现是微不足道的。

答案 1 :(得分:1)

你看过CollectionChangedEventManager了吗?我今天刚试图处理队列更改时遇到了这个问题。

答案 2 :(得分:0)

据我所知,没有简单的解决方案,因为集合只保存对ocjects的引用,因此无法知道,如果集合所持有的对象的属性已更改。

一般来说,你必须选择:

1 :)你让你的集合控制的对象触发事件。您在Charles Petzold的this MSDN article中找到的示例实现。他定义了一个“ObservableNotifiableCollection”。

2 :)如果集合所持有的类型不在您的控制之下(因此您无法自己实现PropertyChangedEvent),则可以使用代理对象。您可以在此处找到示例实现:“Implement InotifyPropertyChanged with Castle.DynamicProxy”。