Should I Unsubscribe from Events

Should I unsubscribe from events?

1) It depends. Usually it's a good idea, but there are typical cases where you don't need to. Basically, if you are sure that the subscribing object is going to outlive the event source, you ought to unsubscribe, otherwise this would create an unnecessary reference.

If however your object is subscribing to its own events, like in the following:

<Window Loaded="self_Loaded" ...>...</Window>

--then you don't have to.

2) Subscribing to an event makes additional reference to the subscribing object. So if you don't unsubscribe, your object might be kept alive by this reference, making effectively a memory leak. By unsubscribing you are removing that reference. Note that in the case of self-subscription the problem doesn't arise.

3) You can do like that:

this.PropertyChanged += PropertyChangedHandler;
...
this.PropertyChanged -= PropertyChangedHandler;

where

void PropertyChangedHandler(object o, PropertyChangedEventArgs e)
{
switch (e.PropertyName)
{
case "FirstName": break;
case "LastName": break;
}
}

is it necessary to unsubscribe from events?

This is the important part from the MSDN documentation that you should take into consideration

To prevent your event handler from
being invoked when the event is
raised, simply unsubscribe from the
event. In order to prevent resource
leaks, it is important to unsubscribe
from events before you dispose of a
subscriber object. Until you
unsubscribe from an event, the
multicast delegate that underlies the
event in the publishing object has a
reference to the delegate that
encapsulates the subscriber's event
handler. As long as the publishing
object holds that reference, your
subscriber object will not be garbage
collected.

Should I unsubscribe from events when publisher and handler are the same object?

This doesn't appear to be necessary.

Based off your comment it sounds like you're most worried about garbage collection (or possible lack of).

I just wrote up a super quick test app inspired by this answer in order to test whether the object was garbage collected. It appears to have been.

Here is the code I used to test (running in Release), using the same code you have for your Foo class (left out for simplicity):

class Program
{
[STAThread]
static void Main()
{
Foo foo = new Foo();

WeakReference fooRef = new WeakReference(foo);

Console.WriteLine(fooRef.IsAlive); //Displays "True"

foo = null;
GC.Collect();

Console.WriteLine(fooRef.IsAlive); //Displays "False"

Console.ReadKey();
}
}

Output:

True

False

Here's a fiddle that seems to do the job as well (assuming it doesn't have its own garbage collection quirks... I'm not a super experienced "fiddler").

Is it always safe to unsubscribe from an event inside the handler?

To clarify the other answer a bit:

Events are based on delegates (in almost all cases). Delegates are immutable. This applies to multicast delegates, too.

When invoking an event the delegate is loaded and then invoked. If the field that the delegate is stored in is modified then this does not affect the already loaded delegate.

It's therefore safe to modify the event from the handler. Those changes will not affect the currently running invocation. This is guaranteed.

All of this only applies to events backed by a delegate. C# and the CLR support custom events that could do anything at all.

Unsubscribing from events - unsubscription or null?

Is this approach correct ... for some reason events are actually adding...

To prevent your event handler from being invoked when the event is raised, you need to
unsubscribe from the event. In order to help prevent any resource leaks, you should unsubscribe from events, read more here about this.

As for your comment about, for some reason events are actually adding, the reason for this is you are not unsubscribing and therefore the object is kept alive by this reference. In return, doing this without unsubscribing would create a memory leak.

As already mention in the comments, do not assign null to the event as, "it will unsubscribe ALL handlers, even ones that your code didn't subscribe." as Matthew Watson has pointed out. Jon Skeet notes, it'll effectively clear the list of subscribers, which means no handlers whatsoever are called at this point, Matthew Watson also mentions this in his comments.

With all this in mind, -= is the proper way of unsubscribing an event and should be used.

References:

How to subscribe to and unsubscribe from events c#

Should I unsubscribe from events

unsubscribing from events

Yes you can, but if the eventhandler is defined in your own class, and also defined in the same instance, then you do not have to unsubscribe from the event, since the publisher and subscriber are the same object. Therefore, no extra objects are held in reference.

If you subscribe object A to handle an event of object B, then it is worth to unsubscribe from the event in object B. Otherwise the multicast delegate that underlies the event will hold references to both objects. And that will prevent the garbage collector from collecting both objects.

C# Should you unsubscribe from static events inside static classes to prevent memory leaks?

If the event usage is through the entire application life cycle then there is no need to worry about unsubscribing.

Once the application exit, the process ends and the memory is purged by the OS, so there is no memory leak after an application has ended.



Related Topics



Leave a reply



Submit