My class contains an object from Interop and calls a method on it which causes it to alloc stuff. It also exposes a method to free that stuff, so I expect I should call this in Dispose():
class MyClass : IDisposable
{
private DllName.ComClassName comInstance;
void SomeMethod()
{
comInstance = new DllName.ComClassName();
comInstance.AllocStuff();
}
public void Dispose()
{
comInstance.FreeThatStuff();
}
}
Now, I should expand all that to follow the Dispose pattern. I have no other disposable or unmanaged resources to release, so assuming comInstance is managed (isn't that what Interop does, wraps unmanaged into managed?), I think the pattern disolves to:
public void Dispose()
{
if (comInstance != null)
{
comInstance.FreeStuff();
comInstance = null;
}
}
Which leaks unless I explicitly call Dispose() on instances of MyClass, which would make the Dispose pattern flawed? So does that mean comInstance must be unmanaged, and the pattern disolves to:
public void Dispose()
{
DisposeComInstance();
GC.SuppressFinalize(this);
}
~MyClass()
{
DisposeComInstance();
}
private void DisposeComInstance()
{
if (comInstance != null)
{
comInstance.FreeStuff();
comInstance = null;
}
}
EDIT:
Implement the dispose pattern for a derived class Instead, to clean up a derived class, you provide the following: A protected override void Dispose(bool) method that overrides the base class method and performs the actual cleanup of the derived class. This method must also call the base. Dispose(bool) ( MyBase.
public void Dispose() { Dispose(disposing: true); // This object will be cleaned up by the Dispose method. // Therefore, you should call GC. SuppressFinalize to // take this object off the finalization queue // and prevent finalization code for this object // from executing a second time.
If you access unmanaged resources (e.g. files, database connections etc.) in a class, you should implement IDisposable and overwrite the Dispose method to allow you to control when the memory is freed.
Dispose improves performance and optimizes memory by releasing unmanageable objects and scarce resources, like Graphics Device Interface (GDI) handles used in applications with restricted Windows space. The Dispose method, provided by the IDisposable interface, implements Dispose calls.
Ultimately you want this kind of pattern:
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
~MyClass()
{
Dispose(false);
}
private void Dispose(bool disposing)
{
if (disposing)
{
// Dispose of disposable objects here
}
// Other unmanaged cleanup here which will be called by the finalizer
if (comInstance != null)
{
comInstance.FreeStuff();
comInstance = null;
}
// Call base dispose if inheriting from IDisposable class.
base.Dispose(true);
}
For a great article on why, check out Implementing IDisposable and the Dispose pattern properly.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With