2014-03-25 39 views
12

這裏是情況。在某些情況下,我發現自己想要一門課程,我們稱它爲class C,它具有與class A相同的功能,但是除此之外它還實現了interface B。現在,我不喜歡這樣寫道:會您可以將接口連接到指定的類

class C : A,B 
{ 
    //code that implements interface B, and nothing else 
} 

的問題,如果class A碰巧被密封。有沒有一種辦法可以讓class A實施interface B,而不必定義class C(擴展方法或某事)

+0

你*控制*'A',或者這是一些第三方組裝? –

+0

@MichaelPerrenoud它是第三方 –

回答

8

基本上沒有。這是「mixins」可能帶來的一部分,但C#語言目前不支持(已經討論了幾次,IIRC)。

你將不得不使用當前的做法,或(更常見)只是封裝A而不是繼承A直通裝飾。

class C : IB 
{ 
    private readonly A a; 
    public C(A a) { 
     if(a == null) throw new ArgumentNullException("a"); 
     this.a = a; 
    } 

    // methods of IB: 
    public int Foo() { return a.SomeMethod(); } 
    void IB.Bar() { a.SomeOtherMethod(); } 
} 
3

我看到的唯一方法,就是改變繼承聚集,像這樣:

class C : B 
{ 
    public C(A instanceToWrap) 
    { 
     this.innerA = instanceToWrap; 
    } 

    //coda that implements B 

    private A innerA; 
} 

似乎有可能在運行時注入接口,因爲它與Array類和IEnumerable<T>接口完成,但它似乎有點矯枉過正。

+0

雖然這是一個有效的解決方法(我發現自己實際使用的解決方法),但這不是我所問的。另外,在某些情況下會導致問題。仍然感謝您回答 –

+0

@MarioStoilov沒有其他設計唯一的方法。你有什麼特別的問題?至於接口注入方法,我會在我回家時嘗試測試它,並可能更新我的答案。 – BartoszKP

+0

看看我對Michaels的評論回答 –

0

你可以嘗試沒有繼承創建類:class C : B和包裝周圍A

此外,您可以提供隱式轉換運算符,以便像A obj = new C(new A())這樣的代碼的工作方式類似於派生類的工作方式。

class C : B 
{ 
    private A _inner; 
    public C(A inner) 
    { 
     this._inner = inner; 
    } 

    public A Inner { get { return this._inner; } } 

    public static implicit operator A(C obj) 
    { 
     return obj == null ? (A)null : obj._inner; 
    } 

    public static implicit operator C(A obj) 
    { 
     return new C(obj); 
    } 
} 
2

有沒有一種辦法可以讓A類實現界面B1,而不必定義C類(擴展方法或某事)

簡短的回答是沒有。您不能使A工具B因爲您沒有控制A。不過,我認爲你正在用擴展方法走向正確的道路。試想一下:

public static class AImplementsBExtensions 
{ 
    public static void Func1(this A o) { } 
    public static void Func2(this A o) { } 
} 

現在顯然我不知道什麼樣的方法上存在B,但是這是如何實現的AB當你不能從它繼承。

請記住,這是不是一個實現。如果您從界面添加或刪除方法,您必須在此處手動完成。但現在你可以做到這一點:

var a = new A(); 
a.Func1(); 
+0

雖然我知道我可以添加這些方法的擴展方法,我要求'(A是B)'是正確的。一個例子是我想'ObservableCollection'在WinRT中實現'ISupportIncrementalLoading'。只是添加方法沒有在那裏工作,所以我最終使用我在我的問題中提到的方式(因爲'ObservableCollection'沒有密封) –

相關問題