通用接口约束



我有一个关于泛型和在创建concret类时使用接口转换的问题:


namespace MyNamespace
{
    interface ITest
    {
    }
    class Timpl : ITest
    {
    }
    class Test<T> where T : ITest
    {
        public T get()
        {
            return default(T);
        }
    }
    class MyClass
    {
        public MyClass()
        {
            Test<ITest> s = new Test<Timpl>(); //Does not compile
        }
    }
}

我读到了协变和反变,但我一定错过了什么,或者它与我正在尝试的无关,或者它只是不起我正在尝试做的作用。

我想我可以从测试到测试进行转换,因为TImple继承了ITest。

应该是

class Test<T> where T : ITest
{
    public T get()
    {
        return default(T);
    }
}

然后创建一个类似的Test实例

var s = new Test<Timpl>();

编辑:

基于以下评论。好的,现在你要处理的是协方差和反方差。如果需要指定

Test<ITest> s = new Test<Timpl>();

那么它就不能工作了,因为只有接口和委托的泛型类型参数才能被标记为协变或逆变。

但是,您可以通过使Test实现一个接口来解决这个问题。

interface ITestClass<out T>
{
    T get();
}
class Test<T> : ITestClass<T> where T : ITest
{
    public T get()
    {
        return default(T);
    }
}
ITestClass<ITest> s = new Test<Timpl>(); // Does compile

试试这个。

namespace MyNamespace
{
    interface ITest
    {
    }
    class Timpl : ITest
    {
    }
    class Test<T> where T : ITest
    {
        public T get()
        {
            return default(T);
        }
    }
    public class mycls : ITest
    {
    }
    class MyClass
    {
        public MyClass()
        {
            Test<mycls> s = new Test<mycls>(); //will compile
        }
    }
}

我想我理解你的问题。您可以在以下MSDN链接上阅读有关协方差和方差的信息:http://msdn.microsoft.com/en-us/library/vstudio/ee207183.aspx

我的问题解决方案看起来像这个

接口ITest{}

class TImpl:ITest
{
}
interface ITest<out T>
{
    T get();
}
class Test<T>:ITest<T> 
          where T:ITest
{
    public T get()
    {
        return default(T);
    }
}

正如您所看到的,我在Test类上添加了和接口,并将Type参数T标记为out。现在您可以执行以下操作:

 ITest<ITest> t = new Test<TImpl>();

我希望这能帮助

最新更新