确定字段是否为泛型类型

时间:2011-08-13 14:04:04

标签: c# .net reflection

是否可以通过反射确定某个字段是否为泛型类型?

如果有可能,怎么办呢?

我想我的问题不够明确,所以我现在正在编辑它。

修改

如果a的类型定义如下例所示, DID NOT 具有Holder<T>类型的实例,但只有System.Type实例通过System.Reflection.Assembly.GetTypes检索并且描述字段_instance的System.Reflection.FieldInfo实例,如何确定_instance字段是否为泛型类型

public class Holder<T>
{
   private T _instance;
}

3 个答案:

答案 0 :(得分:6)

如果您想知道该字段本身是否为泛型类型,则可以使用字段的FieldInfo来检查FieldType属性的IsGenericType属性。

 var info = type.GetField("myField",BindingFlags.Private);
 if (info != null)
 {
      if (info.FieldType.IsGenericType)
      {
           Console.WriteLine( "The type of the field is generic" );
      }
 }

如果要检查字段是否是泛型类定义中泛型的类型,那么您将要检查IsGenericParameter。

 var info = type.GetField("myField",BindingFlags.Private);
 if (info != null)
 {
      if (info.FieldType.IsGenericParameter)
      {
           Console.WriteLine( "The type of the field is the generic parameter of the class" );
      }
 }

当然,您可以将这些结合起来。检查该字段是否是通用定义类中的类型的泛型,更有问题,但仍然可以完成。您只需检查泛型类型的类型参数,以查看其中一个是否设置了IsGenericParameter。请注意,以下示例仅深度为一级;如果你想要全面的东西,你想要定义一个方法并递归地使用它。

var info = type.GetField("myField",BindingFlags.Private);
if (info != null)
{
     if (info.FieldType.IsGenericType)
     {
         foreach (var subType in info.FieldType.GetGenericArguments())
         {
             if (subType.IsGenericParameter)
             {
                 Console.WriteLine( "The type of the field is generic" );
             }
         }
     }
}

答案 1 :(得分:2)

试试

field.GetType().IsGenericType

Type.IsGenericType Property

  

获取一个值,该值指示当前类型是否为泛型类型。

答案 2 :(得分:1)

让我按照我理解的方式重新提出你的问题:

  

我有一个泛型类型,我想知道某个字段类型是否包含(一个)类型参数。我该怎么做?

如果要查明某个类型是否为通用参数,可以使用the IsGenericParameter property。这会为true返回T,但List<T>会返回 。如果你想要,你可以使用递归:

bool ContainsGenericParameter(Type fieldType)
{
    return fieldType.IsGenericParameter ||
        fieldType.GetGenericArguments().Any(t => ContainsGenericParameter(t));
}

例如,如果你有这样的类型:

public class Holder<T>
{
   private T _t;
   private int _int;
   private List<T> _listT;
   private List<int> _listInt;
}

此查询

typeof(Holder<>)
    .GetFields(BindingFlags.NonPublic | BindingFlags.Instance)
    .Select(f => new { f.Name, Generic = ContainsGenericParameter(f.FieldType) })

会返回这样的内容:

Name     Generic
_t       True
_int     False
_listT   True
_listInt False