哪个更好,何时:使用语句或在 C# 中的 IDisposable 上调用 Dispose()?
假设我有以下内容:
using(var ctx = DataContextFactory.Create(0))
{ ... Some code ... }
为什么不直接执行以下操作并丢失几个大括号?:
var ctx = DataContextFactory.Create(0);
ctx.Dispose();
谢谢您的建议!
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!
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(5)
第一个更好。 即使抛出异常,它也确保它被释放,并且它正确处理
Create(0)
返回 null 的情况(即它不会尝试调用Dispose()
在空实例上)。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 (i.e. it doesn't attempt to callDispose()
on a null instance).using
语句总是更好,因为...Dispose()
,即使代码演变成不同的代码路径Dispose()即使出现异常,
也会被调用。 它还会在调用Dispose()
之前检查null
,这可能很有用(假设您不只是调用new
)。using
的一个不明显的(对我来说)技巧是,当您有多个一次性对象时,如何避免过度嵌套:VS code 格式化程序将使两个语句在同一列中开始。
事实上,在某些情况下,你甚至不必重复使用语句...
但是,在同一行上声明多个变量的限制适用于此,因此类型必须相同,并且不能使用隐式类型 var。
A
using
statement is always better because...Dispose()
, even as the code evolves into different code pathsDispose()
gets called even if there's an exception. It also checks fornull
before callingDispose()
, which may be useful (assuming you're not just callingnew
).One non-obvious (to me, anyway) trick with
using
is how you can avoid excessive nesting when you have multiple disposable objects:The VS code formatter will leave the two statements starting in the same column.
In fact, in some situations you don't even have to repeat the using statement...
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.
在可能的情况下,请使用
using
来了解 Marc 引用的原因。 OTOH,这不是一个脑死亡的解决方案,因为有时对象的生命周期不能定义为词法范围,因此请合理使用它。Where you can, use
using
for the reasons Marc cites. 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.唯一不想使用 using 块的地方是一次性对象的作用域位于函数之外的地方。 在这种情况下,您的类应该实现 IDisposable 并在其 Dispose() 中处置该对象。
The only place you don't want to use a using block is where the disposable object is scoped outside of the function. In this case, your class should implement IDisposable and dispose of the object in its Dispose().
using 语句为您提供了良好的语法和异常保护。 您不能在不调用 Dispose 的情况下离开 using 语句(它会转换为调用 dispose 的 finally 块)。 在第二种情况下,如果 Create 和 Dispose 之间出现异常,则不会直接调用 dispose。 除非您使用非托管资源,否则这不是问题,但如果使用,则会发生泄漏。
The using statement gives you nice syntax plus exception protection. You cannot leave the using statement without calling Dispose (it translates into a finally block with a call to dispose). In your second scenario, if you had an exception between the Create and the Dispose, you would not call dispose directly. Which is not a problem unless you are using unmanaged resources, but if you are, you will leak.