When do we need to call Dispose() in dot net c#? - c#

Do I need to dispose a sqldatareader after it is created?
SqlDataReader reader;
---
---
---
reader.Close();
reader.Dispose();

Rule of thumb: if a class implements IDisposable you should always call the Dispose method as soon as you have finished using this resource. Even better wrap it in a using statement to ensure that the Dispose method will be called even if an exception is thrown:
using (var reader = conn.ExecuteReader())
{
...
}

Object which are Disposable can be best used (if possible) in a using block. At the end of the using block, the object is automatically disposed.
Because of memory management it is always advised do dispose your objects if you don't need them anymore.
Here's some stuff to read from the MSDN.

It is recommended to use the using pattern when dealing with anything that implements IDisposable
using ()
{
// use it here
}
This will look after the try..catch..finally construct and calling Dispose.
EDIT I had previously said that I thought Close and Dispose did the same thing for readers (stream, file, sqldatareader etc.) but it appears this is not true looking at the documentation on SQLDataReader so my assumption was wrong.

There is a simple guideline: if you have finished with an object whose type implements IDisposable then call Dispose() on it; you should use a using block to do this.

Related

using statements are always necessary? Or It can be avoid? [duplicate]

I usually use code like this:
using (var connection = new SqlConnection(ConfigurationManager.ConnectionStrings["MyConn"].ConnectionString))
{
var command = connection.CreateCommand();
command.CommandText = "...";
connection.Open();
command.ExecuteNonQuery();
}
Will my command automatically disposed? Or not and I have to wrap it into using block? Is it required to dispose SqlCommand?
Just do this:
using(var connection = new SqlConnection(ConfigurationManager.ConnectionStrings["MyConn"].ConnectionString))
using(var command = connection.CreateCommand())
{
command.CommandText = "...";
connection.Open();
command.ExecuteNonQuery();
}
Not calling dispose on the command won't do anything too bad. However, calling Dispose on it will suppress the call to the finalizer, making calling dispose a performance enhancement.
The safest policy is to always call Dispose() on an object if it implements IDisposable, either explicitly or via a using block. There may be cases where it is not required but calling it anyway should never cause problems (if the class is written correctly). Also, you never know when an implementation may change meaning that where the call was previously not required it is now definitely required.
In the example you've given, you can add an extra inner using block for the command, as well as maintaining the outer using block for the connection.
Yes, you should, even if it the implementation is currently not doing much, you don't know how it is going to be changed in the future (newer framework versions for instance). In general, you should dispose all objects which implement IDisposable to be on the safe side.
However, if the operation is deferred and you don't control the full scope (for instance when working asynchroneously, or when returning an SqlDataReader or so), you can set the CommandBehavior to CloseConnection so that as soon as the reader is done, the connection is properly closed/disposed for you.
In practice, you can skip Dispose. It doesn't free any resources. It doesn't even suppress finalization since the SQLCommand constructor does that.
In theory, Microsoft could change the implementation to hold an unmanaged resource, but I would hope they'd come out with an API that gets rid of the Component base class long before they'd do that.
You can find out this kind of stuff using Reflector or dotPeek or https://referencesource.microsoft.com/.
I had a small dig (I would suggest that you dig yourself though to be fully sure of the rest of this though as I didn't try that hard) and it looks like when you kill a connection there is no disposal of any children associated with that connection. Furthermore it doesn't actually look like the disposal of a command actually does that much. It will set a field to null, detach itself from a container (this may prevent a managed memory leak) and raise an event (this might be important but I can't see who is listening to this event).
Either way it's good practice to use this stuff in a using block or to ensure you dispose of it using a dispose pattern in the object that holds the connection (if you intend to hold onto the command for a while).
In my opinion, calling Dispose for both SqlConnection and SqlCommand is good practice, use below code
using(var connection = new SqlConnection(ConfigurationManager.ConnectionStrings["MyConn"].ConnectionString))
try{
using(var command = connection.CreateCommand())
{
command.CommandText = "...";
connection.Open();
command.ExecuteNonQuery();
}
}
catch(Exception ex){ //Log exception according to your own way
throw;
}
finally{
command.Dispose();
connection.Close();
connection.Dispose();
}

PetaPoco.Database implements IDisposable, so why don't most examples have a 'using' statement?

The PetaPoco.Database object implements IDisposable but I rarely if ever see code samples (including on PetaPoco's own website) that include a using statement as follows:
using (var db = new Database("MyConnectionString"))
{
// Do database stuff
}
Most often I simply see:
var db = new Database("MyConnectionString");
// Do database stuff
// I never see .Dispose() called.
How should PetaPoco.Database objects actually be handed?
As a simple rule: if a class implements IDisposable then go ahead and wrap it in a using. They may not actually be using any unmanaged resources, but it won't hurt and might future-proof you against changes.
PetaPoco maintainer here. Dispose is the same as calling CloseSharedConnection(). However, c# syntax only supports using(...) with IDisposable. For instance IDBConnection, from memory, supports both Close and Dispose.
Basically, it boils down to choice
Example 1
using(var db = new PetaPoco())
{
// some code
}
Example 2
var db = new PetaPoco()
try
{
// code
}
finally
{
db.CloseSharedConnection();
}
It depends on what are you implementing. A Database object it's a connection to the database, you don't want to dispose the connection every time you execute a sql statement in the database because the performance will be terrible.
If you are implementing a web based solution, you typically use one Database object per request, but that request surely execute several sql statements in different filters, global filters and in several controller's methods, so you can't use Using
GC calls Object.Finalize.
IDisposable is not called by GC, it has to be called manually. GC has nothing to do with using and IDisposable
IDisposable tells GC what to do when it wants to get rid of an object.
using asks GC to get rid of an object when its scope ends.
using using with an object that's not IDisposable is useless.

implementing IDisposable interface and what happens when exception is thrown

I have a class that implements the interface IDisposable. My understanding is that when you have finished using the object (something like the line below) the Dispose method is called to make sure everything is cleaned up - is that correct?
myObj = null;
I also would like to know if an exception is thrown whether the Dispose method still gets called? Or should I just be using a 'using' block?
My understanding is that when you have finished using the object (something like the line below) the Dispose method is called to make sure everything is cleaned up - is that correct?
No, it is not correct. Setting an instance of an object to null will not call its Dispose method, you should do that explicitly when you're done with an object.
myObj.Dispose();// Im done with myObj!
This is often done by utilizing using
using(var myObj = new MyObject())
{
myObj.DoSomething();
} // Dispose automatically called.
The above ensures Dispose is called, even if an exception is thrown within the using block.
Dispose should be explicitly called if want to release the system resources used by this object at that particular moment . If we are not calling the Dispose , the system will take care of this at some point with Garbage Collector .
If an object implementes System.IDisposable then we will be able to call the dispose method on it.
Using will be converted in to try, finally block by CLR and the dispose method will be called the in the finally block to release the resources.
Check this link for all information you required like how system handles this and all Using Statement
Just copying the code from the mentioned link to make it more useful.
If you have some code like this
using (MyResource myRes = new MyResource())
{
myRes.DoSomething();
}
Then it get's automatically converted to
MyResource myRes= new MyResource();
try
{
myRes.DoSomething();
}
finally
{
// Check for a null resource.
if (myRes!= null)
// Call the object's Dispose method.
((IDisposable)myRes).Dispose();
}

Isn't it redundant to dispose of an object inside its own using block?

While programming over an existent class, I've noticed that someone has written something like this:
using(DisposableObject disp = new DisposableObject())
{
...
...
disp.Dispose()
}
And then I wonder: isn't the using block enough to dispose an object? Could be there any way Dispose() can be useful in such case?
Cause it doesn't make any sense to me...
In your case it is useless to use dispose inside using because when using statement's scope ends it automatically calls dispose. That's why you can only write objects which implements IDisposable Interface inside using brackets.
using(.......)
Moreover if there was any statement using disp object after disp.Dispose() it would give an error, because by then object would have been disposed, i.e. its memory has been released.
But beware
If dispose is last line before using scope ends then it is useless.
But it is not useless when there are more lines after dispose.
Yes, a using block is actually equivalent to and an alternative syntax for:
var d = new DisposableObject();
try
{
d.DoSomething();
}
finally
{
if(d != null)
((IDisposable)d).Dispose();
}
Note that it uses finally instead of something like 'catch'. The finally-clause will always be executed, even if there's an exception.
using is enough. There is no reason to call Dispose twice.
There are two reasons why you can use Dispose inside a using block:
you want to dispose the object before the using block ends. In this case the using block is a "safety net" that ensures you that your object will be disposed even if an exception happens. (using behaves like a try block which has a finally block in which your object is disposed)
calling Dispose makes more clear what you're doing. This is typical, i.e. of
transaction scopes:
using(TransactionScope ts=new TransactionScope)
{
...
if (cond)
{
ts.Complete();
}
else
{
ts.Dispose(); // makes it clear you're rolling back the transaction
}
}
This call to Dispose it's not neccesary, but it's "explanatory". It makes more obvous that the transaction is rolled back.
#Nikhil Agrawal is right. One thing I need mention is when you implement Idisposable interface, you should make sure it can be invoked many times. That's mean you should do some validation.

Some advanced questions on the using statement

I know there are a number of threads on here about how to use the using statement and calling the Dispose() method. I have read the majority of these threads.
If I call Dispose(), does it call Close()?
If I want to use an object (say SqlDataReader), but then use it again in another code block, should I not call Dispose()? Which also means to omit the using statement.
Also, to clarify, if a FileStream is wrapping a StreamWriter and I call dispose on the FileStream, this will call Flush(), Close() and Dispose() (depending on whether Dispose() calls Close()) on the StreamWriter, right? Likewise, if I call Close on the FileStream, this will only call Flush() and Close() on the FileStream.
Is checking IL a good way to answer these questions about what is happening under the hood?
"If I call Dispose(), does it call Close()?"
In theory, it should. The BCL classes all do this, but it is up to the library author to correctly handle this. If the library you are using is done correctly, Dispose() should also Close() [and Close() will Dispose() - the calls should be interchangable].
"If I want to use an object (say SqlDataReader), but then use it again in another code block, should I not call Dispose()? Which also means to omit the using statement."
Correct. If you use the using statement, it will always call Dispose(). This will close the data reader before your other block can use it.
"Also, to clarify, if a FileStream is wrapping a StreamWriter and I call dispose on the FileStream, this will call Flush(), Close() and Dispose() (depending on whether Dispose() calls Close()) on the StreamWriter, right? Likewise, if I call Close on the FileStream, this will only call Flush() and Close() on the FileStream."
If you are wrapping a FileStream around a StreamWriter, I highly recommend treating them consistently. Use a single using statement with both members, so they are both disposed of at the end of the block. This is the safest, most clean approach.
"Is checking IL a good way to answer these questions about what is happening under the hood?"
It is a way - although a more difficult way. Read up on MSDN about using and streams, and the documentation will explain it in simpler terms than trying to parse the IL. The IL will tell you EXACTLY what happens, though, if you are curious.
If I call Dispose(), does it call Close()?
Close() and Dispose() do the same if implemented properly; it is just a naming thing. It sounds more plain to close a file than to dispose it. See Implementing Finalize and Dispose to Clean Up Unmanaged Resources esspecialy 'Customizing a Dispose Method Name'.
If I want to use an object (say SqlDataReader), but then use it again in another code#
block, should I not call Dispose()? Which also means to omit the using statement.
Yes, because the object gets disposed on exiting the using block.
Also, to clarify, if a FileStream is wrapping a StreamWriter and I call dispose on the > FileStream, this will call Flush(), Close() and Dispose() (depending on whether Dispos()
calls Close()) on the StreamWriter, right? Likewise, if I call Close on the FileStream, > this will only call Flush() and Close() on the FileStream.
It is the other way; a StreamWriter is based on an underlying stream an closing the StreamWriter closes the underlying stream that may be a FileStream; see the MSDN for reference. Hence a single using statement for the StreamWriter is sufficent.
If I call Dispose(), does it call Close()?
Calling Dispose should take any required actions to dispose of the resource, which should be similar, if not identical to, calling Close. This, however, is an implementation detail and not necessarily guaranteed (though we can expect that the BCL follows this guideline).
If I want to use an object (say SqlDataReader), but then use it again in another code block, should I not call Dispose()? Which also means to omit the using statement.
If you want to use the object again, you definitely should not dispose it. However, you should typically use two separate connections if you're going to the database two separate times. It's generally not a good idea to keep an IDataReader around an longer than is needed to grab your needed data.
Also, to clarify, if a FileStream is wrapping a StreamWriter and I call dispose on the FileStream, this will call Flush(), Close() and Dispose() (depending on whether Dispose() calls Close()) on the StreamWriter, right? Likewise, if I call Close on the FileStream, this will only call Flush() and Close() on the FileStream.
Disposing an object that wraps another disposable object should call Dispose on the interior object. Calling Close on a FileStream will call its Dispose method under the good, so it will also act on both streams.
Is checking IL a good way to answer these questions about what is happening under the hood?
Checking IL will definitely answer most of these questions definitively. As #Rich says, you can also just try debugging your own Dispose implementations. There is also, of course, MSDN documentation to start with before you try to figure it out yourself, and Reflector if you don't want to muck around in IL.
If I call Dispose(), does it call Close()?
Not necessarily. I sometimes use Reflector to check what actually happens in Close and Dispose.
If I want to use (...) it again in another code block, should I not call Dispose()?
Correct. Call Dispose when you're done. But that doesn't mean you always want to keep your object alive for a long time - you can sometimes benefit from creating multiple instances (multiple using constructs) -- e.g. You might wan to close a connection as soon as possible, but then create a new one again when you need it.
As you said, there are lot of resources on that, but I will include the MSDN link for some guidelines: Implementing Finalize and Dispose to Clean Up Unmanaged Resources.
An easier way to debug this than going through the IL code would be to derive from your IDisposable, override the necessary methods doing nothing but calling base.[Method Name](), and set a breakpoint in each one. Then if you wrap your derived class in a using block, you'll see the lifecycle of these calls.
No, IDisposable does not require Close(), but the object implementing IDispose may be nice enough to include it in the Dispose() method.
You should dispose it as soon as you have the piece of data you are getting from the DB. Don't leave a reader open any longer than you need. If you are doing any real work with the data, use a dataAdapter/dataset instead of reader.
No Idea. Check the Generated IL
I try to move the using clause higher up, since I prefer to use that syntax. Then call the other blocks using that resource from inside that using block.

Categories

Resources