2017-06-15 73 views
2

我已经检查了一些关于反射和重载方法的其他文章,但可以找到任何帮助。我找到的一篇文章是this one,但这并没有太大的帮助。C#反射,获取重载方法

我有以下两种方法:

1 | public void Delete<T>(T obj) where T : class { ... } 
2 | public void Delete<T>(ICollection<T> obj) where T : class { ... } 

我试图让法N°1。

我试了一下经典的GetMethod("Delete")的方法,但是因为有两个方法用这个名字Ambiguous -Exception被抛出。我尝试使用其他参数(如GetMethod("Delete", new [] { typeof(Object) }))指定方法模式,但没有找到任何内容(空返回)。

我想我可能只是循环所有的方法,并检查参数。

我写了下面的方法...

public static IEnumerable<MethodInfo> GetMethods(this Type type, String name, Type schemaExclude) 
    { 
     IEnumerable<MethodInfo> m = type.GetRuntimeMethods().Where(x => x.Name.Equals(name)); 
     return (from r in m let p = r.GetParameters() where !p.Any(o => schemaExclude.IsAssignableFrom(o.ParameterType)) select r).ToList(); 
    } 

...返回不包含与schemaExclude类型的参数的方法。

我这样称呼它 GetMethods("Delete", typeof(ICollection))没有按预期工作。

显然..ICollection'1[T]不可转让给ICollection。它也不是IEnumerable,IEnumerable<>ICollection<>。我再一次尝试了typeof(Object),它确实有效,但是确实返回了这两种方法(就像它应该的那样)。

我错过了什么?

return type 
    .GetRuntimeMethods() 
    .Where(x => x.Name.Equals("Delete")) 
    .Select(m => new { 
     Method = m 
    , Parameters = m.GetParameters() 
    }) 
    .FirstOrDefault(p => 
     p.Parameters.Length == 1 
    && p.Parameters[0].ParameterType.IsGenericType 
    && p.Parameters[0].ParameterType.GetGenericTypeDefinition() == typeof(ICollection<>) 
    )?.Method; 

符合以下条件的上述器的方法:

+2

构建在使用反射和询问方法与特定类型的你是不是要求与*兼容*类型的方法,你问带参数的方法参数那些**特定的**类型。您希望在这方面支持的任何继承和接口实现都必须由您的代码处理。所以你要求一个带有“ICollection”参数的“Delete”方法,而且没有。 –

+0

@ LasseV.Karlsen感谢您的评论。是的,这就是我所设想的。这就是为什么我在我写的方法中采用了不同的方法,我尝试检查应该排除的类型是否由参数类型分配。这应该涵盖任何类的继承。你建议检查什么?任何建议采取不同的方法? –

+1

你知道编译时的'T'吗?然后它就是'GetMethods(“Delete”,typeof(ICollection ))''。否则,您必须使用“Type.MakeGenericType”在前面构建运行时类型。 – HimBromBeere

回答

1

您可以通过检查其泛型参数类型,这样查找方法

  • 叫“删除”,
  • 使用单个参数
  • 使用参数作为泛型,
  • With th Ë泛型参数类型从ICollection<>

Demo.

+0

谢谢你的回答!这确实解决了我的问题,但我真正需要从演示中唯一需要的是'ParameterType.IsGenericType'部分。我将我的支票更改为'schemaExclude.IsAssignableFrom(o.ParameterType.IsGenericType?o.ParameterType.GetGenericTypeDefinition():o.ParameterType)'。那就是诀窍 –