将简单对象转换为简单且通用的接口

时间:2018-05-06 12:01:31

标签: c# generics types parameters casting

我正在寻找一种将对象转换为简单接口和从简单接口派生的通用接口的方法。

以下是我的例子:

interface INonGeneric
{

}

interface IGeneric<T> : INonGeneric where T : ITypeParameter
{
    T Build();
}

interface ITypeParameter
{

}

class TypeClass : ITypeParameter
{

}

所以这是我尝试使用的设计。如果我对仿制药的理解存在缺陷,我认为错误对你来说是显而易见的。

然后我创建了我想要使用的类:

class MyClass : MyClassBase<TypeClass>
{
    public override TypeClass Build()
    {
        return new TypeClass();
    }
}

abstract class MyClassBase<T> : IGeneric<T> where T : ITypeParameter
{
    public abstract T Build();
}

然后我尝试像这样投射它们:

void Main()
{
    var myClass = new MyClass();

    var cast1 = myClass as INonGeneric;
    if(cast1 != null) Console.WriteLine("cast 1 works!"); //THIS WORKS
    var cast2 = TestCast<ITypeParameter>(myClass);
    if(cast2 != null) Console.WriteLine("cast 2 works!"); //THIS DOES NOT WORK
}

非常感谢任何帮助。

编辑:对不起,我忘了放入TestCast方法。这是:

IGeneric<T> TestCast<T>(INonGeneric obj) where T : ITypeParameter
{
    return obj as IGeneric<T>;
}

1 个答案:

答案 0 :(得分:3)

由于Covariance问题,这不起作用。 请考虑此示例代码。

var liInt = new List<int>() { 1,2,3};
var liObj = List<object>(liInt);

之后,你可以认真地向liObj添加一些非整数值,显然,这不行。

bool b = false;
liObj.Add(b);

为了防止这种情况,您应该隐式地告诉您仅在返回位置使用通用类型,而不是在输入中。例如:

interface IGeneric<out T> : INonGeneric where T : ITypeParameter

欲了解更多信息,请参阅以下链接: http://tomasp.net/blog/variance-explained.aspx/