尝试/最后阻止vs调用dispose?
这两个代码示例之间是否有任何区别,如果没有,为什么using
存在?
StreamWriter writer; try { writer = new StreamWriter(...) writer.blahblah(); } finally { writer.Dispose(); }
VS:
using (Streamwriter writer = new Streamwriter(...)) { writer.blahblah }
我的意思是在第二个例子中你真的应该把它放在try块中,所以添加finally块确实不会花费太多精力。 我知道整个事情可能包含在一个更大的尝试块中但是,对我来说似乎是多余的。
您的代码存在一些问题 。 永远不要写这样(改为使用 ), 这就是为什么 :
StreamWriter writer; try { // What if you failed here to create StreamWriter? // Eg you haven't got permissions, the path is wrong etc. // In this case "writer" will point to trash and // The "finally" section will be executed writer = new StreamWriter(...) writer.blahblah(); } finally { // If you failed to execute the StreamWriter's constructor // "writer" points to trash and you'll probably crash with Access Violation // Moreover, this Access Violation will be an unstable error! writer.Dispose(); }
当你像那样“使用”时
using (StreamWriter writer = new StreamWriter(...)) { writer.blahblah(); }
它等于代码
StreamWriter writer = null; // <- pay attention to the assignment try { writer = new StreamWriter(...) writer.blahblah(); } finally { if (!Object.ReferenceEquals(null, writer)) // <- ... And to the check writer.Dispose(); }
这两个代码示例之间是否有任何区别
是的,在调用Dispose
之前using
null
检查(即实际代码扩展为引入空检查)。
为什么使用存在?
因为代码更简洁。 只是一个语法糖。
你写的几乎就是using
包装的模式。 因此,这是using
节省必须编写相同的try....finally
阻止每次使用Disposable对象。
至于你编辑过的问题
[…]在第二个例子中你真的应该把它放在try块中,所以添加finally块确实不会花费太多精力
您可能无法(或者不想)明确地处理来自blahblah
错误,您只是想让它冒泡到调用代码……但仍然在清理StreamWriter资源的过程中!
所以你最终得到这个:
StreamWriter writer; try{ writer = new StreamWriter(...) writer.blahblah(); }catch{ throw; // pointless! } finally [ writer.Dispose(); }
后者只是前者的语法糖。 他们应该做同样的事情,但后者需要更少的样板代码。
我建议使用一个一个不太可能犯错误。
他们并不完全一样。 try
/ finally
块不能防止愚蠢的错误。
StreamWriter writer = new StreamWriter(...); try { ... writer = new StreamWriter(...); ... } finally { writer.Dispose(); }
请注意,只有第二个作者被处置。 相反,
using (StreamWriter writer = new StreamWriter(...)) { ... writer = new StreamWriter(...); ... }
将给出编译时错误。
首先, 使用using
比代码更安全 – 它可以正确处理Disposable
对象构造中的错误,并且不会在null对象上调用dispose。
第二个区别在于代码可读性 – 看看你的例子。 第一个版本需要7行。 第二个 – 只有3个。