2013-03-27 81 views
0

編輯: 也許這是一個更清晰,更對這個問題的角度制定:差異在返回類型

在一些通用接口IInterface<T>,我想回到一個泛型類型的對象,其中一個的類型參數應該是IInterface<T>的實現。

public class OtherType<T> {} 
public interface IInterface<T> 
{ 
    OtherType<IInterface<T>> Operation(); 
} 
public class Impl : IInterface<int> 
{ 
    public OtherType<IInterface<int>> Operation() 
    { 
     return new OtherType<Impl>(); 
    } 
} 

由於Impl工具IInterface<int>,它似乎是合理的,我認爲我可以使用這種方式。然而,似乎我不能,我得到的編譯器錯誤

無法轉換表達式類型OtherType<Impl>到返回式OtherType<IInterface<int>>

+0

請問您能否將您非常漫長而令人困惑的類名轉換爲A,B,C等類似的東西? – Sebastian 2013-03-27 08:39:14

+0

@CarlPett:你是否一直關注Eric Lippert在Monads上的精彩博客系列? http://ericlippert.com/2013/02/21/monads-part-one/看來你正在努力重新發明這個構造,並且可以對一般機制有所瞭解。 – 2013-03-27 08:55:16

+0

@PieterGeerkens:我沒有,謝謝你的提示!看起來很有趣。我只有時間閱讀前四部分,但到目前爲止,我真的不知道如何在這裏應用它? – carlpett 2013-03-27 16:37:17

回答

1

問題是OtherType<T>是一類和一般類不允許在C#中CO /逆變。一般interfaces這樣做,只要out類型不出現在任何輸入位置,並且in類型不出現在任何輸出位置。在你的代碼示例中,你可以通過引入一個標記爲covariant的附加接口來獲得它,然後改變你的返回類型。

public interface IOtherType<out T> {} // new 
public class OtherType<T> : IOtherType<T> { } 

public interface IInterface<T> 
{ 
    IOtherType<IInterface<T>> Operation(); // altered 
} 
public class Impl : IInterface<int> 
{ 
    public IOtherType<IInterface<int>> Operation() 
    { 
     return new OtherType<Impl>(); 
    } 
} 

不管這實際上與你的其他方法定義適合你的使用情況的東西只有自己知道,在有限的關於您的代碼段的細節。

+0

謝謝,我會試試看。雖然有趣的是「有限的細節」,但是......我的第一個表述包含了我正在使用的具體類型的細節,然後我因爲有太多不相關的上下文而遭到了打擊:P – carlpett 2013-03-27 18:51:08

+0

按照我的意願工作,完美! – carlpett 2013-03-28 07:35:53

1

OtherType<IInterface<int>>並不意味着「工具」 - 它有點意思「是用泛型類型參數Interface<int>OtherType,但是這不是你怎麼說

如果你只是想確保返回類型實現IInterface<int>然後設置爲返回類型:

public interface IInterface<T> 
{ 
    IInterface<T> Operation(); 
} 

public class Impl : IInterface<int> 
{ 
    public <IInterface<int>> Operation() 
    { 
     return new OtherType(); 
    } 
} 

其中

public class OtherType : IInterface<int> 
{} 

這意味着你可以返回一個實現IInterface<int>任何類型。

否則,你可以把它多一點約束上調用使用泛型類型約束:

public interface IInterface<T> 
{ 
    TRet Operation<TRet>() where TRet : IInterface<T>; 
} 

public class Impl : IInterface<int> 
{ 
    public TRet Operation<TRet>() where TRet : IInterface<int> 
    { 
     return new OtherType(); 
    } 
} 

這意味着你可以約束操作返回一個特定的類,它反過來又實現IInterface<int>

它會被稱爲:

Impl i = new Impl(); 
OtherType x = i.Operation<OtherType>();