Reputation: 37633
Can someone explain why #1 approach is better than #2?
try
{
}
catch
{
}
finally
{
reader.Close();
dataStream.Close();
response.Close();
}
try
{
reader.Close();
dataStream.Close();
response.Close();
}
catch
{
}
Upvotes: 0
Views: 664
Reputation: 520
If an exception occurs anywhere in your try block before all the objects are closed, they won't be closed. The finally block allows you to perform clean-up should an exception be raised in your try block.
As others have mentioned, the using
approach is the way I go with my own code. The compiler translates the using
into try{} finally{}
blocks for you. Check out the following MSDN link: http://msdn.microsoft.com/en-us/library/yh598w02.aspx
Cheers.
Upvotes: 0
Reputation: 3680
Since a Try block is designed to handle possible failures, it's important to handle both a successful and unsuccessful case. Items inside the Try block might get called, they might not - depending on if and where a failure takes place.
By placing closure statements into the finally block, you ensure the statements will always be called, whether or not the Try section was successful. This way, you won't leave reader, datastream, and response left open - even if a failure did take place.
Upvotes: 0
Reputation: 120380
I prefer approach 3
using(var reader = ...)
using(var dataStream = ...)
using(var response = ...)
{
//...
}//all disposed (and implicitly closed) at the end of this scope
Using this construct, the compiler converts to approximately this:
var reader = ...;
var dataStream = ...;
var response = ...;
try
{
//...
//even if an error happens here
}
finally
{
//this code still runs before control leaves this method.
reader.Close();
dataStream.Close();
response.Close();
}
Upvotes: 4
Reputation: 564323
If reader.Close()
raises an exception, both of your options will never close dataStream
or response
.
However, in your #2 option, if code prior to reader.Close()
raises an exception, no objects will be closed. In #1, you at least guarantee that you'll call reader.Close()
always, even if something else raises an exception.
In general, though, any object with a Close()
method should also implement Close
via IDisposable.Dispose()
, in which case I would always prefer to use using
instead of either of these options:
using(var reader = CreateReader())
{
using(var dataStream = CreateDataStream(reader))
{
using(var response = CreateResponse(dataStream))
{
// Use objects
}
}
}
This will enforce that all objects are properly closed, but is cleaner.
Upvotes: 7