看到這個。爲什麼顯式轉換爲IDisposable?這只是簡短的確保在退出使用塊時調用IDisposable?將類型轉換爲IDisposable - 爲什麼?
using (proxy as IDisposable)
{
string s = proxy.Stuff()
}
看到這個。爲什麼顯式轉換爲IDisposable?這只是簡短的確保在退出使用塊時調用IDisposable?將類型轉換爲IDisposable - 爲什麼?
using (proxy as IDisposable)
{
string s = proxy.Stuff()
}
這個「竅門」,如果你可以這樣稱呼它,很可能是由於proxy
是編譯器無法驗證的類型,實際上實現了IDisposable
。
有關using
指令的好處是,如果該參數是null
,然後Dispose
沒有呼叫將在退出using
聲明範圍之內完成。
所以,你已經顯示的代碼實際上是短手:
var disposable = proxy as IDisposable;
try
{
string s = proxy.Stuff();
}
finally
{
if (disposable != null)
disposable.Dispose();
}
換句話說,它說:「如果這個對象實現IDisposable,我需要的時候,我用做處置它下面這段代碼。「
這是不必要的,因爲using
語句明確地綁在IDisposable
接口,per the MSDN docs
提供了一個方便的語法,確保正確使用IDisposable的對象。
編輯:本C# language spec(秒8.13)提供了用於using
語句的語法糖三種可能的擴展:
形式
using (ResourceType resource = expression) statement
的使用語句對應於三種可能的擴展之一。當的ResourceType是一個非空值類型,膨脹是
{
ResourceType resource = expression;
try {
statement;
}
finally {
((IDisposable)resource).Dispose();
}
}
否則,當的ResourceType是一個空值類型或大於動態其它引用類型,膨脹是
{
ResourceType resource = expression;
try {
statement;
}
finally {
if (resource != null) ((IDisposable)resource).Dispose();
}
}
否則,當ResourceType爲動態時,擴展爲
{
ResourceType resource = expression;
IDisposable d = (IDisposable)resource;
try {
statement;
}
finally {
if (d != null) d.Dispose();
}
}
請注意,在這些擴展中的每一個擴展中,無論如何都會進行轉換,因此如前所述,as IDisposable
是不必要的。
如果您從某處獲得proxy
實例並且其靜態類型未實現IDisposable
,但您知道真實類型可以執行並且您希望確保它將被放置在
public class Proxy : ISomeInterface, IDisposable
{
...
}
private ISomeInterface Create() { ... }
ISomeInterface proxy = Create();
//won't compile without `as`
using(proxy as IDisposable)
{
...
}
如果「proxy」是程序員「知道」的對象實現IDisposable,但編譯器無法驗證它會怎麼樣?爲什麼演員不需要呢? – 2011-01-14 20:37:36
是的,如果有什麼理由讓讀者清楚`proxy`擴展IDisposable – Will 2011-01-14 20:37:37
只要他的代理不是WCF代理,在這種情況下使用using塊是不安全的。但那是另一個話題。 – 2011-01-14 20:38:23