C#泛型 - 从泛型类调用泛型方法

时间:2011-02-02 17:12:55

标签: c# generics casting explicit

我有以下类,我试图从ExportFileBaseBL类调用Compare方法但是我收到错误

无法将类型'Class1'隐式转换为'T'。存在显式转换(您是否错过了演员?)

public abstract class Class1<T> where T: Class2
{
    public abstract Class1<T> Compare(Class1<T> otherObj);
}

public abstract class Class3<T, U> where T: Class1<U>
                         where U: Class2
{
    public T Compare(T obj1, T obj2)
    {
        if (obj1.Prop1 > obj2.Prop1)
        {
            return obj1.Compare(obj2); // Compiler Error here
        }
        else
        {
            return obj2.Compare(obj1);  // Compiler Error here
        }
    }

}

类型转换不应该隐含吗?我错过了什么吗?

2 个答案:

答案 0 :(得分:4)

问题是您的抽象Compare方法被定义为接受Class1<T>类型的参数并返回Class1<T>的实例,而不是更具体的< / em>类型比Class1<T> 。但这是您的Class3.Compare方法尝试执行的操作:调用T.Compare并假设输出为T,实际上您只能确定它是{{1} }}

为了提供一个更简单,更易于理解的例子,假设我有这个类:

Class1<U>

上面的代码假设类似于您自己的错误假设:class Parser { public abstract object Parse(string text); } class Int32Parser { public int Parse(Parser parser, string text) { return parser.Parse(text); } } 只返回parser.Parse,因为int派生自int(就像您的情况一样, object必须来自T);事实上,您只能确定它会返回Class1<U>

我可以通过两种方式来解决此问题:将object作为通用方法:

Class1<T>.Compare

...或者放宽public abstract U Compare<U>(U otherObj) where U : Class1<T>; 方法返回值的类型特异性:

Class3.Compare

就个人而言,除非你绝对需要第一个,否则我更喜欢第二个。当复杂性开始像这样增长时,所有这些泛型类型约束都会变得非常混乱,并且比你期望的更多。

答案 1 :(得分:2)

使用您在班级声明的参数类型调用方法。

  return obj1.Compare<T>(obj2); 

您还需要将Compare方法的定义设为通用:

public abstract Class1<T> Compare<T>(Class1<T> otherObj);