Standard event handler (with operator +=
) is one of the memory leakage cause (if it is not unregistered/disposed (with -=
operator)).
And Microsoft solved it with WeakEventManager
and its inheritance like: PropertyChangedEventManager, CollectionChangedEventManager, CurrentChangedEventManager, ErrorsChangedEventManager
and so on.
The simple example code with memory leakage is:
public class EventCaller
{
public static event EventHandler MyEvent;
public static void Call()
{
var handler = MyEvent;
if (handler != null)
{
handler(null, EventArgs.Empty);
Debug.WriteLine("=============");
}
}
}
public class A
{
string myText;
public A(string text)
{
myText = text;
EventCaller.MyEvent += OnCall;
// Use code below and comment out code above to avoid memory leakage.
// System.Windows.WeakEventManager<EventCaller, EventArgs>.AddHandler(null, "MyEvent", OnCall);
}
void OnCall(object sender, EventArgs e)
{
Debug.WriteLine(myText);
}
~A()
{
Debug.WriteLine(myText + " destructor");
}
}
void Main()
{
var a = new A("A");
var b = new A("B");
EventCaller.Call();
a = null;
GC.Collect();
EventCaller.Call();
}
The output is:
A
B
+++++++
A
B
+++++++
We can see that the destructor will not be called.
But if we change (by commenting the unused code) from:
EventCaller.MyEvent += OnCall;
to
System.Windows.WeakEventManager<EventCaller, EventArgs>.AddHandler(null, "MyEvent", OnCall);
And the output is:
A
B
+++++++
B
+++++++
A destructor
B destructor
After A is nulled then its event handler will not be called anymore.
A and B will be disposed after not be used anymore without -=
operator.
Can I safely replace all += operator with System.Windows.WeakEventManager
to avoid memory leakage due to probably missing event unregistration and saving code by should not implement IDisposable
?
If it is not really safe, what should I consider or notice?
See Question&Answers more detail:
os 与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…