SqlConnection.Close() внутри оператора using
Все ваши ответы были полезны. Спасибо всем, кто приложил усилия, чтобы ответить на мой вопрос. Приветствия:)
Я использую этот код:
public void InsertMember(Member member)
{
string INSERT = "INSERT INTO Members (Name, Surname, EntryDate) VALUES (@Name, @Surname, @EntryDate)";
using (sqlConnection = new SqlConnection(sqlConnectionString_WORK))
{
sqlConnection.Open();
using (SqlCommand sqlCommand = new SqlCommand(INSERT, sqlConnection))
{
sqlCommand.Parameters.Add("@Name", SqlDbType.VarChar).Value = member.Name;
sqlCommand.Parameters.Add("@Surname", SqlDbType.VarChar).Value = member.Surname;
sqlCommand.Parameters.Add("@EntryDate", SqlDbType.Date).Value = member.EntryDate;
sqlCommand.ExecuteNonQuery();
}
}
}
Это неправильно, если я не добавляю sqlConnection.Close();
, прежде чем удалять его? Я имею в виду... Он не показывает никаких ошибок, никаких проблем вообще... Лучше ли сначала закрыть его? Если да, то почему?
Ответы
Ответ 1
Не нужно Close or Dispose
блок using
позаботится об этом для вас.
Как указано в MSDN:
Следующий пример создает SqlConnection, открывает его, отображает некоторые его свойств. Соединение автоматически закрывается в конце используемого блока.
private static void OpenSqlConnection(string connectionString)
{
using (SqlConnection connection = new SqlConnection(connectionString))
{
connection.Open();
Console.WriteLine("ServerVersion: {0}", connection.ServerVersion);
Console.WriteLine("State: {0}", connection.State);
}
}
Ответ 2
using statement ensures that Dispose is called
, даже если исключение возникает, когда вы вызываете методы на объекте. You can achieve the same result by putting the object inside a try block and then calling Dispose in a finally block
; на самом деле, вот как оператор using переводится компилятором. MSDN
Итак, в конечном итоге ваша строка кода
using (sqlConnection = new SqlConnection(sqlConnectionString_WORK))
будет преобразован в обычный try finally block
путем вызова компилятора IDisposable object in the finally
Ответ 3
Оператор using - это блок finally try, и в вашем случае последний блок будет иметь вызов connection.Dispose()
. Таким образом, вам действительно не нужен независимый оператор connection.Close()
.
Преимущество заключается в том, что это обеспечивает удаление даже в случае исключения, поскольку блок finally всегда будет работать.
try
{
sqlConnection.Open();
// ....
}
finally
{
if(sqlConnection != null)
sqlConnection.Dispose();
}
Ответ 4
Нет, это не так. SqlConnection закроет соединение после того, как он пройдет с помощью блока и вызовет метод Dispose. SqlConnection.Dispose(), равный методу SqlConnection.Close().
Из MSDN: Если SqlConnection выходит из области действия, он не будет закрыт. Поэтому вы должны явно закрыть соединение, вызвав Close или Dispose. Close и Dispose являются функционально эквивалентными.
Ответ 5
Вы используете Using
, который будет Dispose()
для вас.
Если вы используете соединение вне инструкции Using
, тогда да - вам нужно закрыть соединение по завершении.
Ответ 6
В соответствии с документацией MSDN для метода Close
:
вы должны явно закрыть соединение, вызвав Закрыть или Dispose. Закрыть и Dispose являются функционально эквивалентными.
Поэтому вызов Dispose
(неявно, даже, используя using
) будет как бы закрывать ваши базы.
Стоит также отметить, что я считаю, хотя и не конкретным для вашего случая, что Close
всегда будет эффективно вызываться, когда вещь обернута в оператор using
, что может быть не так, если оно должно быть опущено и исключение происходит без правильной обработки try
/catch
/finally
.
Ответ 7
Неправильно, если я не добавляю sqlConnection.Close(); перед удалением его
Нет, это не так, пока вы используете свое соединение в Using
. Когда вы выйдете из области использования, Dispose
вызывается для соединения sql. который закроет существующее соединение и освободит все ресурсы.
Ответ 8
Это очень интересный вопрос и не столь очевидный, как многие думают. Использование оператора будет корректно работать для соединения только в том случае, если будут удалены все объекты, которые используют соединение. Некоторое время назад у нас возникла проблема с открытыми соединениями на нашем сервере sql. Все выглядело отлично, потому что соединения находились внутри с помощью операторов, но один из разработчиков создал несколько методов с SqlDataReader и не закрыл его правильно. Из-за этого соединения не были выпущены.
Причиной этого является то, как работает сборщик мусора. Короче говоря - он создает карту объектов для размещения и фактически распоряжается ими, когда нет активных ссылок на эти объекты.