The finalize
method can be suppressed in .NET by calling the method GC.SuppressFinalize().
By suppressing, you mean that the finalize method will not be triggered
for that particular object by the garbage collector
Why is this suppression required? Normally releasing of unmanaged resources
can happen in two ways. One being the finalize method and other being
the dispose method. If you are releasing unmanaged resources using dispose
method, then you have to ensure that garbage collector does not call finalize
method.
If it triggers
finalize method, then it is redundant and unnecessary call since the resources
are already cleaned up using dispose method. Hence while implementing
dispose method you will use this method GC.SuppressFinalize() to suppress
the finalize method. This is demonstrated with an example which is shown
below:
public class
sampleClass {
public class sampleDisposeClass: IDisposable {
public System.IO.StreamReader sampleReader;
System.ComponentModel.Component sampleComponent =
new System.ComponentModel.Component();
bool disposeFlag
= false;
public void Dispose() {
DisposeResources(true);
GC.SuppressFinalize(this);
}
public static
void Main() {
sampleDisposeClass obj = new sampleDisposeClass();
obj.sampleReader = new System.IO.StreamReader("sample.txt");
string eachLine;
while ((eachLine = obj.sampleReader.ReadLine()) != null) {
Console.WriteLine(eachLine);
}
Console.ReadLine();
}
}
Output of
this example will contain the contents of sample.txt file.
In this example,
you do the following:
Created
a class called sampleClass which has a nested class called sampleDisposeClass
The nested class has implemented the IDisposable interface in order
to implement the Dispose method.
The nested class sampleDisposeClass has two resources as its members.
The StreamReader object sampleReader is an unmanaged resource and the
component sampleComponent is a managed resource. Both these resources
have to be cleaned up using Dispose method.
Define Dispose method such that it calls your newly created method
DisposeResources. Pass the Boolean value true while triggering the later
method. True signifies that managed resources have to be cleaned up.
Inside Dispose method, you have to make a call to GC.SuppressFinalize
to prevent finalization being done by the garbage collector using finalize
method.
Define the method DisposeResources such that it cleans up both
managed resources and unmanaged resources used by the current object.
Managed resource will be disposed only if the Boolean flag disposeManagedRes
passed as a parameter to the method has its value to be true.
Define the destructor for the sampleDisposeClass which will be
triggered only if the Dispose method is not triggered. The destructor
should clean up only unmanaged resources and not managed resources. Hence
you call DisposeResources from inside the destructor with the parameter
value as false to ensure that managed resources are not cleaned up explicitly
through destructors.
Outside the nested class and inside the sampleClass you define
the Main method which creates an instance of the nested class sampleDisposeClass
and accesses the unmanaged resource the StreamReader instance.