Dispose pattern improvement?

A

Andreas Huber

Hi there

Is there a reason why .NET framework base classes implementing IDisposable
(like e.g. System.ComponentModel.Component) do not prevent multiple calls to
the protected virtual void Dispose( bool disposing ) function?

Derived classes would then no longer need to check whether they have been
disposed already and the associated bool member wouldn't be necessary
either.

Example code:

class Base : IDisposable
{
private bool disposed = false;

~Base()
{
if ( !this.disposed ) // *** here ***
{
Dispose( false );
this.disposed = true;
}
}

public void Dispose()
{
if ( !this.disposed ) // *** here ***
{
Dispose( true );
GC.SuppressFinalize( this );
this.disposed = true;
}
}

public void SomeMethod()
{
if ( this.Disposed )
{
throw new ObjectDisposedException( "Base" );
}

// ...
}

// This property is necessary so that subclass methods can check whether
// the object has been disposed.
protected bool Disposed
{
get { return this.disposed; }
}

protected virtual void Dispose( bool disposing )
{
if ( disposing )
{
// release my managed resources
}

// release my unmanaged resources
}
}


class Derived : Base
{
public void SomeOtherMethod()
{
if ( this.Disposed )
{
throw new ObjectDisposedException( "Derived" );
}

// ...
}

protected override void Dispose( bool disposing )
{
try
{
if ( disposing )
{
// release my managed resources
}

// release my unmanaged resources
}
finally
{
base.Dispose( disposing );
}
}
}
 
J

Jon Skeet

Andreas Huber said:
Is there a reason why .NET framework base classes implementing IDisposable
(like e.g. System.ComponentModel.Component) do not prevent multiple calls to
the protected virtual void Dispose( bool disposing ) function?

Derived classes would then no longer need to check whether they have been
disposed already and the associated bool member wouldn't be necessary
either.

In what way would the associated bool member not be necessary? You'd
still need to check whether or not the object had been disposed for
methods *other* than dispose itself (eg writing to a stream which has
already been disposed).
 
A

Andreas Huber

Jon said:
In what way would the associated bool member not be necessary? You'd
still need to check whether or not the object had been disposed for
methods *other* than dispose itself (eg writing to a stream which has
already been disposed).

I'm not sure I understand what you mean as that's what the protected
Disposed property in the base class would be for...

I quote from my original message:
class Base : IDisposable
{ [snip]
// This property is necessary so that subclass methods can check whether
// the object has been disposed.
protected bool Disposed
{
get { return this.disposed; }
} [snip]
[snip]
class Derived : Base
{
public void SomeOtherMethod()
{
if ( this.Disposed )
{
throw new ObjectDisposedException( "Derived" );
}

// ...
}
[snip]

Regards,

Andreas
 
J

Jon Skeet

Andreas Huber said:
I'm not sure I understand what you mean as that's what the protected
Disposed property in the base class would be for...

Ah - sorry, I thought you were suggesting that the bool member in your
example wouldn't be necessary. I wasn't entirely clear about what you
were suggesting...
 
A

Andreas Huber

Jon said:
Ah - sorry, I thought you were suggesting that the bool member in your
example wouldn't be necessary. I wasn't entirely clear about what you
were suggesting...

I see, sorry for being unclear...

Regards,

Andreas
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top