我可以从返回类型的类型中提取Generic的类型吗?

时间:2012-11-11 02:57:47

标签: c# generics

所以,我有这种方法:

public ICollection<String> doSomething() { }

目前,我正在尝试检查方法的返回类型是否为ICollection类型。但是,在C#中,我必须在检查时传入通用。所以我不能这样说,“方法是ICollection”。

问题是我不想在检查时限制泛型的类型。在Java中,我可以使用通配符,但我不能在C#中这样做。我曾经想过尝试使用Type.GetGenericParamterContraints()并试图将它的第一个结果粘贴在ICollection的通用约束中进行检查,但这也没有用。有人有什么想法吗?

isCollection(MethodInfo method){
    Type[] ret = method.ReturnType.GetGenericParametersContraint();
    Type a = ret[0];
    return method.ReturnType is ICollection<a>;
}

编辑:添加了我尝试的内容。

5 个答案:

答案 0 :(得分:1)

你应该可以这样做:

MethodInfo method = ... // up to you
var returnType = method.ReturnType;

var isGenericICollection = returnType == typeof(ICollection<>);

答案 1 :(得分:1)

使用Type.GetGenericTypeDefinition(),并将其结果与typeof(ICollection<>)进行比较。

因此,要检查方法的返回类型是否为ICollection,您可以这样做:

method.ReturnType.GetGenericTypeDefinition() == typeof(ICollection<>)

顺便说一下。 method.ReturnType is ICollection<a>永远不会成立,因为is检查第一个操作数的类型是否是第二个操作数的子类型。 ReturnType类型为Type,但不是某些ICollection的子类型。

答案 2 :(得分:1)

如果允许它是非通用System.Collections.ICollection(也由ICollection<T>实现)那么它只是:

typeof(System.Collections.ICollection).IsAssignableFrom(method.ReturnType)

如果您只想与通用ICollection<T>进行比较(我认为没有理由,但您可能有理由):

method.ReturnType.IsGenericType 
  && typeof(ICollection<>)
  .IsAssignableFrom(method.ReturnType.GetGenericTypeDefinition())

请注意,如果返回类型是非泛型的,则不起作用。因此,如果有一个类实现ICollection<T>但它本身不是通用的,那么它将不起作用。这意味着它不会捕获class Foo : ICollection<string>,但它捕获class Foo<T> : ICollection<T>

第一种方式会很好地抓住两者。

答案 3 :(得分:0)

试试这个,使用MethodInfo.ReturnType确定返回类型

Use the below method, call `isCollection<string>(method)` 

public static bool isCollection<T>(MethodInfo method)
{
    return method.ReturnType.Equals(typeof(ICollection<T>));
}

答案 4 :(得分:0)

试试这个:

class Program
{
    public ICollection<string> Foo() { return new List<string>(); } 
    public static bool TestType()
    {
        MethodInfo info = typeof(Program).GetMethod("Foo");

        return info.ReturnType.GetGenericTypeDefinition() == typeof(ICollection<>);
    }
    static void Main(string[] args)
    {
        Console.WriteLine("{0} is ICollection<> : {1}", "Foo", TestType());
    }
}

打印Foo is ICollection<> : True