Business/Data design, IDisposable, and using statement?

G

Guest

I trying to determine the best pattern for designing my business and data
layers...

Can the instance of the business object eventually cause memory leaks in
Example 1? If your business class doesn't implement IDisposable and falls
out scope, does it eventually get cleaned up by the GC or should it be set to
NULL?

If it can cause leaks, should the IDisposable always be implemented at a
base class level as a best practice?

If it does implement IDisposable, is wrapping the using statement (Example
2) in a try block to catch any exceptions the proper technique? I see
samples of "using" but not many of how to handle an exception if it occurs in
the using block.

EXAMPLE 1
-------------
MyBizClass myBizClass = null;
try
{
myBizClass = new MyBizClass();
return myBizClass.GetSomeDataFromDataLayer();
}
catch
{
throw;
}
finally
{
//Set myBizClass = null???
}

EXAMPLE 2
--------------

try
{
using (MyBizClass myBizClass = new MyBizClass())
{
return myBizClass.GetSomeDataFromDataLayer();
}
}
catch
{
throw;
}
 
N

Nicholas Paldino [.NET/C# MVP]

Dave,

You should use IDisposable only when you have the need for controlling
the lifetime of an object, most likely as the result of using a resource
which can not just be left in an undisposed state (such as a file handle,
unmanaged memory, a database handle, etc, etc).

I also use IDisposable on structures when I want to have deterministic
finalization semantics in a method.

Your class doesn't seem to be doing either, so I would not implement
IDisposable. Also, setting a variable to null (not a field, a variable)
will actually prolong the lifetime of the object in code compiled for
release mode.

Hope this helps.
 
M

Michael S

Dave said:
I trying to determine the best pattern for designing my business and data
layers...

Oki. And it seems like you think you must try... and catch..
Can the instance of the business object eventually cause memory leaks in
Example 1? If your business class doesn't implement IDisposable and falls
out scope, does it eventually get cleaned up by the GC or should it be set to
NULL?

It will be cleaned up by the GC. At some time... In seconds, hour or days...
Why IDisposable is sometimes important. As for sql connections or filehandles.

If you open a file for writing, you can't wait for the GC to (maybe) kick in and remove the filehandle in the destructor (finalizer) of the object. The file will be locked until the stream is collected.
If it can cause leaks, should the IDisposable always be implemented at a
base class level as a best practice?

Your objects typically won't leak. Only if you start allocating resources that must (should) be disposed of after its direct use you should implement IDsposable.

Hence, If you have a class that sports the metod save, and that opens a stream, writes and call .Dispose() you should not implement IDisposable yourself.

But, if you create a class with the methods Open(string filename), Write(string stuff) and Close(), you should implement IDisposable.
EXAMPLE 1
-------------

This does nothing. catching and throwing does what?
And as your ? says in your finally comment. What should it do?

You're doing nothing with your try, catch, finally..
Just rewrite it into:

public SomeData DoStuff()
{
MyBizClass myBizClass = new MyBizClass();
return myBizClass.GetSomeDataFromDataLayer();
}
EXAMPLE 2
--------------

You think you have to implement IDisposable. Well you don't.
So don't focus on the caller, let's have a look att the method being called...

it should look something like this:

public SomeData GetSomeDataFromDataLayer();
{
using (SqlConnection conn = SomeConnectionFactory.Create())
{
//etc etc
}
}

SqlConnection implements IDisposable, and by using the using syntactic suggar, you have actually done something like this:

public SomeData GetSomeDataFromDataLayer();
{
Try
{
SqlConnection conn = SomeConnectionFactory.Create())
//etc etc
}
finally
{
conn.Dispose(); // no matter what, the sql connection will be returned to the pool.
}
}

Hope this makes it clearer for you.

Happy Coding
- Michael S
 
N

Nick Hounsome

A simple set of rules for when you need to implement IDisposable is:

1-the common one) If your class owns any object that implements IDisposable
then it must implement IDisposable and Dispose must call Dispose on those
objects.

2-the less common one) If you your class holds any "handle" to a resource
obtained by some interop call then you must implement IDisposable to release
that resource. [You should write a class whose sole purpose it to own that
handle and to wrap the interop calls associated with it.]

3) If some object gives you a handle then see 2 - but this should never
happen because the design sucks.
 

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