-
Notifications
You must be signed in to change notification settings - Fork 0
Disposable
Correctly implementing the dispose pattern can be a tedious and error-prone task to do over and over again. In .NET the IDisposable interface provides the public interface for it, but implementing it correctly involves a lot more than just writing a Dispose()
method.
The Disposable
base class saves you from doing all the hard work yourself. It is a complete and thread-safe implementation of the dispose pattern that serves as an almost drop-in replacement for IDisposable
.
Instead of implementing IDisposable
yourself your classes just extend Disposable
:
// Wrong
public class demo : IDisposable
{
public void Dispose()
{
}
}
// Good
public class demo : Disposable
{
public override void Dispose(bool disposing)
{
}
}
The body of Dispose(bool disposing)
follows the dispose pattern. When the object is disposed the value of the disposing
parameter will be true. When this is the case, any unmanaged resources will be disposed:
public class demo : Disposable
{
private IDisposable propertyToDispose;
public override void Dispose(bool disposing)
{
if (disposing)
{
this.propertyToDispose.Dispose();
}
}
}
Calling methods on disposed objects can lead to unwanted state changes and data corruption. To prevent that, all public methods must check the disposed state before modifying any internal or external data.
Dispose
provides two ways of doing that. The first and recommended one is calling ThrowIfDisposed()
as the very first statement inside a method. If just checks if the object is disposed, and if it is it throws an ObjectDisposedException
.
public class demo : Disposable
{
private IDisposable propertyToDispose;
public void DoSomething()
{
this.ThrowIfDisposed();
}
}
If you want to write your own checks you can use the IsDisposed
property. Its value is true when the object is disposed, and false otherwise.
public class demo : Disposable
{
private IDisposable propertyToDispose;
public void DoSomething()
{
if (this.IsDisposed)
throw new ObjectDisposedException();
// Do something
}
}