Finalize Memory Management and Garbage Collection

119 • No overhead is incurred unless the heap becomes exhausted. • It is impossible for applications to cause memory leaks. • The application need not be careful with circular references. Although the process of garbage collection is expensive on the order of a fraction of a second when it occurs, Microsoft claims that the total overhead of garbage collection is on average much less than the total overhead of reference counting as shown by their benchmarks. This, of course, is highly dependent on the exact pattern of object allocation and deallocation that occurs in any given program.

3.9.1 Finalize

Many objects require some sort of cleanup i.e., finalization when they are destroyed. An example might be a business object that maintains a connection to a database. When the object is no longer in use, its database connection should be released. The .NET Framework provides a way for objects to be notified when they are about to be released, thus permitting them to release nonmemory resources. Memory resources held by the object can be ignored because they will be handled automatically by the garbage collector. Heres how it works: the Object class defined in the System namespace has a method called Finalize that can be overridden. Its default implementation does nothing. If it is overridden in a derived class, however, the garbage collector automatically calls it on an instance of that class when that instance is about to be reclaimed. Heres an example of overriding the Finalize method: Public Class SomeClass Protected Overrides Sub Finalize Release nonmanaged resources here. MyBase.Finalize Important End Sub End Class The Finalize method should release any nonmanaged resources that the object has allocated. Nonmanaged resources are any resources other than memory for example, database connections, file handles, or other OS handles. In contrast, managed resources are object references. As already mentioned, it is not necessary to release managed resources in a Finalize method—the garbage collector will handle it. After releasing resources allocated by the class, the Finalize method must always call the base classs Finalize implementation so that it can release any resources allocated by base-class code. If the class is derived directly from the Object class, technically this could be omitted because the Object classs Finalize method doesnt do anything. However, calling it doesnt hurt anything, and its a good habit to get into. An objects Finalize method should not be called by application code. The Finalize method has special meaning to the CLR and is intended to be called only by the garbage collector. If youre familiar with destructors in C++, youll recognize that the Finalize method is the identical concept. The only difference between the Finalize method and C++ destructors is that C++ destructors automatically call their base class destructors, whereas in Visual Basic .NET, the programmer must remember to put in the call to the base classs Finalize method. It is interesting to note that C—another language on the .NET platform—actually has destructors as C++ does, but they are automatically compiled into Finalize methods that work as described here.

3.9.2 Dispose