Click here to Skip to main content
15,881,715 members
Please Sign up or sign in to vote.
0.00/5 (No votes)
MSDN recommends disposing any variable of type System.Drawing.Brush before its last reference is released. Otherwise, the resources it is using will not be freed until the garbage collector calls the Brush object's Finalize method.

As we know, local variables are destroyed automatically when the control flow goes out of the scope of the method it belongs. So, is it necessary to dispose a brush object every time if it is local?
Posted

Yes.
Items are not "destroyed automatically" when they go out of scope - they are just unavailable for use. The actual object you created on the heap with the new keyword remains on the heap, and uses up system resources (the brush handle) as well as the memory for the rest of the brush class. The heap object is not destroyed until the Dispose method is called - and if you don't do it then it waits around until the garbage collector is kicked in and destroys it as an unreferenced variable. This could be minutes, hours, or even years later.

If a class implements IDisposable, then you should always Dispose of instances when you no longer need them, either by calling Dispose yourself, or by enclosing the create and usage in a using block.

One of the frequent mistakes is not to do this for a file based Stream: which means that the file it is connected to remains open until the garbage collector frees it up - and your own program can't open it again as it already has an exclusive lock on the file!
 
Share this answer
 
v2
The answer is most definately yes, you should call dispose on them when you are done with them.

The .NET garbage collector doesn't get around to cleaning up objects immediately when the method goes out of scope. The collector (in versions prior to 4.5) runs on a separate thread and only gets to it when the system does garbage collection. In versions prior to 4, the garbage collector blocks the main thread while it cleans up the trash.

This means that you could be calling enough code that you aren't actually freeing the GDI resources fast enough, and you will run out of GDI resources or make your application slower as the garbage collector determines if those references are really used or not (the garbage collector is a reference counting system).

So yes, it is important to call Dispose on an object that needs to free resources when you are done with it. This is true for all objects that implement IDisposable, not just GDI ones.
 
Share this answer
 
Comments
Sergey Alexandrovich Kryukov 9-Nov-13 19:55pm    
I'm not sure that your explanation is correct. I think GDI resources are unmanaged, that's why they are not touched by a GC at all, so the reclaiming mechanism is based on (unrelated) disposal.

That said, the answer is certainly yes.

Also, "cleaning up objects immediately when the method goes out of scope" is not directly related to IDispose. In .NET, there are no cleaning mechanism based on leaving a stack frame. Instead, the scope of "using" operator can be used, but it happens only if the developers uses the "using" operator with IDisposable objects.

—SA
Ron Beyer 9-Nov-13 22:04pm    
As always I appreciate the opportunity to second guess myself :). Did a lot of research into this and here's what I found:

Reference Specifically the section "Manipulating Unmanaged Resources". If an object has a finalizer (which the GDI Pen/Brush base classes do, I looked up the source to make sure :) ), the finalizer will be called when the object is GC'd. The process about which this happens is explained further up in the document but in a nutshell the GC marks the object and adds the finalizer to the queue for finalization. Proper implementation of the finalizer will call Dispose and dispose the managed objects. Since the managed classes are wrappers around unmanaged code, they are collected when the reference count hits zero (goes out of scope).

Another resource which shows a little longer discussion (ignore the comment in the first answer about IDisposable for unmanaged resources, which explained underneath is false), but primarily the points are that GC will eventually call the finalizer, and in the case of a Brush/Pen the GDI+ resources will be released. However because of the non-deterministic nature of the GC system, when this happens is entirely up to fate. The problem in not disposing yourself is that you run the risk of eating up GDI resources faster than the GC is calling Finalize (and therefore being released by the pen itself, not GC). This can look like a memory or resource leak, but its much more apparent if you look at GDI objects while your program is executing.

So you are right, GC does not touch unmanaged resources, but it will call a finalizer, and as long as that finalizer is properly coded, it will release any unmanaged resources. It just takes a LOT longer that way.

And no, IDisposable doesn't have anything to do with scope or when objects are ready to be collected (.Dispose() doesn't signal the GC). GC is reference counting so an object that has no references is collected, which is what happens if it is out of scope, again longer than if you had marked it as not referenced yourself...

Sorry for being long winded :)
Sergey Alexandrovich Kryukov 9-Nov-13 23:07pm    
Very good. Perhaps you need to clarify the body of your answer, to avoid misleading of OP or false impression of misunderstanding. It does not have to be as detailed as your last comment, which you can strip from reasoning...
—SA
priyamtheone 23-Nov-13 8:52am    
Thanks for the clarification.

This content, along with any associated source code and files, is licensed under The Code Project Open License (CPOL)



CodeProject, 20 Bay Street, 11th Floor Toronto, Ontario, Canada M5J 2N8 +1 (416) 849-8900