У меня такой вопрос: если у меня есть метод MethodInfo для метода, полученного из типа интерфейса, и у меня также есть объект Type для класса, который реализует этот интерфейс, но он реализует указанный метод с помощью явная реализация, как правильно получить соответствующий объект MethodInfo для метода реализации в этом классе?
Причина, по которой мне нужно это сделать, заключается в том, что к реализующим методам могут быть применены некоторые атрибуты, и мне нужно найти их с помощью отражения, но класс, которому нужно найти эти атрибуты, имеет только ссылку на объект для реализующего класса, и объект Type (+ соответствующие объекты MethodInfo) для интерфейса.
Итак, давайте предположим, что у меня есть следующая программа:
using System;
using System.Reflection;
namespace ConsoleApplication8
{
public interface ITest
{
void Test();
}
public class Test : ITest
{
void ITest.Test()
{
throw new NotImplementedException();
}
}
class Program
{
static void Main(string[] args)
{
Type interfaceType = typeof(ITest);
Type classType = typeof(Test);
MethodInfo testMethodViaInterface =
interfaceType.GetMethods()[0];
MethodInfo implementingMethod =
classType.GetMethod(/* ??? */"Test");
Console.Out.WriteLine("interface: " +
testMethodViaInterface.Name);
if (implementingMethod != null)
Console.Out.WriteLine("class: " +
implementingMethod.Name);
else
Console.Out.WriteLine("class: unable to locate");
Console.Out.Write("Press enter to exit...");
Console.In.ReadLine();
}
}
}
Запуск этого дает мне:
interface: Test
class: unable to locate
Press enter to exit...
В коде есть вызов .GetMethod с ??? комментарий. В этой части мне нужна помощь. Либо то, что мне нужно указать здесь (и я много тестировал, что подводит меня к другому пути), либо что мне нужно заменить этот код.
Поскольку я использовал явную реализацию метода из интерфейса, фактическое имя метода не просто «Test». Если я дам дамп всего содержимого массива GetMethods () типа класса, с таким кодом:
foreach (var mi in classType.GetMethods(
BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public))
{
Console.Out.WriteLine(mi.Name);
}
тогда я получаю это:
ConsoleApplication8.ITest.Test <-- this is the one I want
ToString
Equals
GetHashCode
GetType
Finalize
MemberwiseClone
ясно, что имя имеет полное имя интерфейса и пространство имен перед ним. Однако из-за перегрузки мне кажется, что мне нужно найти все такие методы реализации в классе (т. Е. Предположить, что существует несколько методов Test, различающихся по параметрам), а затем сравнить параметры.
Есть ли более простой способ? По сути, я бы хотел, как только у меня будет объект MethodInfo для метода из интерфейса, найти точный метод, который класс, реализующий этот метод, получая его объект MethodInfo.
Обратите внимание, что я нахожусь в зацикленной ситуации, поэтому, если мне придется пройтись по методам в классе, чтобы найти точный метод из интерфейса, это нормально, если у меня есть хороший способ определить, когда я нашел правильный.
Я попытался изменить цикл выше, как это:
foreach (var mi in classType.GetMethods(
BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public))
{
if (mi.GetBaseDefinition() == testMethodViaInterface)
Console.Out.WriteLine(mi.Name);
}
Это ничего не печатало, поэтому ясно, что GetBaseDefinition
в таком методе не указывает на объект MethodInfo из интерфейса.
Есть указатели?