简体   繁体   English

哪个更好,何时:使用语句或在C#中的IDisposable上调用Dispose()?

[英]Which is better, and when: using statement or calling Dispose() on an IDisposable in C#?

Suppose I have the following: 假设我有以下内容:

using(var ctx = DataContextFactory.Create(0))
{ ... Some code ... }

Why not just do the following and lose a couple of curly braces?: 为什么不做以下操作而失去几个花括号?:

var ctx = DataContextFactory.Create(0);
ctx.Dispose();

Thanks for the advice! 谢谢你的建议!

The first is better. 第一个更好。 It ensures it is disposed even if an exception is thrown, and it correctly handles the case where Create(0) returns null (ie it doesn't attempt to call Dispose() on a null instance). 它确保即使抛出异常也会处理它,并且它正确处理Create(0)返回null的情况(即它不会尝试在null实例上调用Dispose() )。

A using statement is always better because... using声明总是更好,因为......

  • you can't forget to call Dispose() , even as the code evolves into different code paths 你不能忘记调用Dispose() ,即使代码演变成不同的代码路径
  • Dispose() gets called even if there's an exception. 即使存在异常,也会调用Dispose() It also checks for null before calling Dispose() , which may be useful (assuming you're not just calling new ). 它还会在调用Dispose()之前检查null ,这可能很有用(假设您不只是调用new )。

One non-obvious (to me, anyway) trick with using is how you can avoid excessive nesting when you have multiple disposable objects: 一个非显而易见的(对我来说,反正)特技using的是你如何能避免过多的嵌套,当你有多个一次性的对象:

using (var input = new InputFile(inputName))
using (var output = new OutputFile(outputName))
{
    input.copyTo(output);
}

The VS code formatter will leave the two statements starting in the same column. VS代码格式化程序将使两个语句从同一列开始。


In fact, in some situations you don't even have to repeat the using statement... 事实上,在某些情况下,你甚至不必重复使用声明......

using (InputFile input1 = new InputFile(inputName1), input2 = new InputFile(inputName2))

However, the restrictions for declaring multiple variables on the same line applies here so the types must be the same and you cannot use the implicit type var . 但是,在同一行上声明多个变量的限制适用于此类,因此类型必须相同,并且不能使用隐式类型var

Where you can, use using for the reasons Marc cites. 在哪里可以using ,因为Marc引用的原因。 OTOH this isn't a brain dead solution as sometimes the lifetime of the object can't be defined as a lexical scope so use it reasonably. OTOH这不是一个脑死亡的解决方案,因为有时候对象的生命周期不能被定义为词汇范围,所以要合理地使用它。

The only place you don't want to use a using block is where the disposable object is scoped outside of the function. 您不想使用using块的唯一地方是一次性对象在功能之外的范围。 In this case, your class should implement IDisposable and dispose of the object in its Dispose(). 在这种情况下,您的类应该实现IDisposable并在其Dispose()中处理该对象。

The using statement gives you nice syntax plus exception protection. using语句为您提供了良好的语法和异常保护。 You cannot leave the using statement without calling Dispose (it translates into a finally block with a call to dispose). 您不能在不调用Dispose的情况下离开using语句(它会转换为带有dispose调用的finally块)。 In your second scenario, if you had an exception between the Create and the Dispose, you would not call dispose directly. 在第二种情况下,如果Create和Dispose之间有异常,则不会直接调用dispose。 Which is not a problem unless you are using unmanaged resources, but if you are, you will leak. 除非您使用非托管资源,否则这不是问题,但如果您使用非托管资源,则会泄漏。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM