我在c#中使用“使用”关键字。
using(SqlConnection sourceConnection = new SqlConnection())
{
sourceConnection.Open();
var destinationConnection = new SqlConnection();
destinationConnection.Open();
}
在上面的代码行中,连接将被释放,或者只有sourceConnection()将被处置。
答案 0 :(得分:3)
仅处理sourceConnection
,即您在using
语句中包装的对象。您应该使用另一个using语句来确保destinationConnection
也被处置:
using (SqlConnection sourceConnection = new SqlConnection())
using (var destinationConnection = new SqlConnection())
{
sourceConnection.Open();
destinationConnection.Open();
}
答案 1 :(得分:3)
using
在IDisposable
界面上运行。忽略变量的范围,它基本上做了类似的事情:
SqlConnection sourceConnection = new SqlConnection();
try
{
sourceConnection.Open();
var destinationConnection = new SqlConnection();
destinationConnection.Open();
}
finally
{
if (sourceConnection != null)
{
sourceConnection.Dispose();
}
}
所以在回答你的问题时,它只能关闭一个。
来自MSDN,来自Robert S的this post:
C#,通过.NET Framework常见 语言运行时(CLR),自动 释放用于存储的内存 不再需要的对象。 内存的释放是 非确定性;内存被释放 每当CLR决定执行时 垃圾收集。但是,确实如此 通常最好释放有限 文件句柄和文件等资源 网络连接速度快 可能。
using语句允许 程序员指定何时对象 使用资源应该发布 他们。提供给使用的对象 声明必须执行 IDisposable接口。这个界面 提供Dispose方法,其中 应该释放对象的资源。
这再次表明它只适用于一个对象:使用的主题。
答案 2 :(得分:2)
只会处理其中一个,您永远不会明确地调用Dispose
或包裹using
destinationConnection
。
你可以这样做,两者都将永远处置。
using(SqlConnection sourceConnection = new SqlConnection())
{
using(SqlConnection destinationConnection = new SqlConnection())
{
}
}
答案 3 :(得分:2)
有些人已经注意到,LRESULT CALLBACK WndProc(HWND hWnd, UINT Msg, WPARAM wParam, LPARAM lParam)
{
switch(Msg)
{
case WM_CREATE:
hButton=CreateWindow("Button","Click Me",WS_CHILD|WS_VISIBLE,70,60,150,30,hWnd,(HMENU) 1,NULL,NULL);
hButton2=CreateWindow("BUTTON","Press here",WS_CHILD|WS_VISIBLE,170,160,250,130,hwnd,(HMENU) 2,NULL,NULL);
break;
case WM_COMMAND:
switch(LOWORD(wParam))
{
case 1:
//What will the first button do?write it here
break;
case 2:
//What will the second button do?write it here
break;
}
break;
}
return 0;
}
包装using
界面,如:
IDisposable
与:
相同using (var foo = new MyDisposable()) { ... }
到目前为止一切顺利。 C#实现此目的的原因是非托管资源。为什么?非托管资源要求您在需要时清理内容,而不是垃圾收集器(GC)需要的时间(当内存不足时为f.ex.)。
暂时考虑替代方案:让我们假设您有一个文件。你打开文件,写一些字节,忘记'关闭',然后没有IDisposable关闭它。即使您不再使用该对象,您的文件仍将继续打开。更糟糕的是,如果您的程序退出,您甚至不知道已写入数据。如果你的程序运行的时间足够长,那么在某些时候GC可能会启动并删除你的东西,但在此之前,每次打开文件的其他尝试都可能会给你一个很大的错误。所以,简而言之......:很多痛苦和痛苦。
这就是var foo = new MyDisposable()
try {
...
}
finally {
if (foo != null) { foo.Dispose(); }
}
解决的问题。
连接,文件,内存访问,网络访问,...基本上所有使用需要清理的东西都会实现IDisposable
。即使如果类型实现了IDisposable
,你也可以更好地处理它。
所以...... SQL连接实现了IDisposable,SQL Readers实现了IDisposable,等等。就个人而言,在使用它之前,我倾向于检查每种类型是否存在IDisposable接口(所以是的:所有时间)。
一旦你理解了这一点,使用这一切的正确方法是显而易见的:
IDisposable
......等等。
现在,在某些情况下,您显然无法使用using (var sourceConnection = new SqlConnection())
{
sourceConnection.Open();
using (var destinationConnection = new SqlConnection())
{
destinationConnection.Open();
// ...
using (var myReader = srcConnection.ExecuteReader(...))
{
// ...
}
}
}
,因为您使用的是不同的方法。怎么解决这个?简单:在具有这些方法的类中实现Dispose Pattern。
更多信息(以及Dispose模式):https://msdn.microsoft.com/en-us/library/b1yfkh5e(v=vs.110).aspx