2011-10-10 93 views
11

比方說,你定義一些任意的接口:強制轉換爲未明確實現的接口?

public interface IInterface 
{ 
    void SomeMethod(); 
} 

而且我們說,有一些類,恰好有一個匹配的公共接口,即使它們不「實施IInterface」。 IE:

public class SomeClass 
{ 
    public void SomeMethod() 
    { 
     // some code 
    } 
} 

有沒有辦法讓IInterface引用到SomeClass實例? IE:

SomeClass myInstance = new SomeClass(); 
IInterface myInterfaceReference = (IInterface)myInstance; 

感謝

回答

13

不,沒有辦法做到這一點。如果類型沒有實現接口,那麼就沒有辦法投射到它。實現類似於所需行爲的最佳方式是創建一個包裝類型,該類型爲SomeClass提供IInterface的實現。

public static class Extensions { 
    private sealed class SomeClassWrapper : IInterface { 
    private readonly SomeClass _someClass; 

    internal SomeClassWrapper(SomeClass someClass) { 
     _someClass = someClass; 
    } 

    public void SomeMethod() { 
     _someClass.SomeMethod(); 
    } 
    } 

    public static IInterface AsIInterface(this SomeClass someClass) { 
    return new SomeClassWrapper(someClass); 
    } 
} 

然後你就可以進行下面的調用

SomeClass myInstance = new SomeClass(); 
IInterface myInterface = myInstance.AsIInterface(); 
+0

它也可以使用反射來找到包裝中的任何類的方法(或拋出異常,如果沒有找到) – Magnus

2

號只是因爲兩班正好有相同名稱的方法,並不意味着他們遵守同一合同。這就是爲什麼您通過明確實施合適的界面來定義合同的原因。

2

SomeClass實現的方法可能與接口中的方法具有相同的簽名,但由於它不繼承/實現接口,因此在此方案中無法使用強制轉換 - 不存在「意外」一致性 - 你必須明確狀態爲每個類實現一個特定的接口。

4

如果您有訪問源,你總是可以裝飾類,如果沒有,你可以做一個包裝:

public class InterfaceWrapper : IInterface 
{ 
    private readonly SomeClass _someClass; 

    public InterfaceWrapper(SomeClass someClass) { _someClass = someClass; } 

    public void SomeMethod() { _someClass.SomeMethod(); } 
} 
+0

它會工作,如果我繼承的類,如果它不密封和實現接口保持繼承類空 –

2

CSScriptLibrary.dll有一種擴展方法,可將對象實例「對齊」到給定接口:

public static T AlignToInterface<T>(this object obj) where T : class; 

還要檢查庫的其餘部分,當涉及到反射C#腳本時,它是一個非常有用的API。

此致敬禮。

相關問題