Как вызвать метод, который принимает входной параметр в качестве другого объекта класса, используя Reflection в C#?(Метод дает исключение аргумента)
Я использую Reflection следующим образом: а) Загрузка сборки б) Получение всех методов и их соответствующих параметров в) Вызов методов
При вызове методов, которые принимают тип ввода как примитивные типы данных (int, double, string и т. Д.), Проблем не возникало. Я попытался вызвать метод двумя способами:
(object)method.Invoke(obj,respar);
где respar - массив входных параметров
object cu = Activator.CreateInstance(typeof(Customer)) as Customer;
respar.SetValue(cu, i);//i = index
а также
(object)type.InvokeMember(methodName, BindingFlags.InvokeMethod | BindingFlags.Instance | BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Default,null, obj, respar);
куда
object obj = Activator.CreateInstance(type,true);//obj
В первом случае я получаю ошибку исключения аргумента, а во втором - метод исключения не найден.
Например, если я вызываю метод, скажем GetCustomer (Данные клиента), где Customer - это класс, вышеупомянутые ошибки выбрасываются.
Позвольте мне объяснить подробно: есть один класс CustomerModel
public class CustomerModel
{
public string FirstName{get;set;}
public string LastName {get;set;}
}
И класс клиента
public class Customer
{
public CustomerModel GetCustomerDetails(CustomerTable tableobj)
{
//TODO: Get customer details from tableobj and pass to CustomerModel Obj
}
}
Я пытаюсь вызвать все методы этого класса клиентов через рефлексию. Есть еще один класс Test:
public class Test
{
public void GetAllMethodsInassembly()
{
//Load assembly
//Get all classes
// Foreach Class=> get all methods
//Invoke each method => get result and store in XML file
}
}
Метод в Customer GetCustomerDetails, который вызывает исключение, как упомянуто. Пожалуйста, предложите.
2 ответа
Вы пытались использовать Type.GetMethod
вместо этого, который возвращает MethodInfo
это имеет Invoke
метод? Более подробная информация здесь: http://msdn.microsoft.com/en-us/library/6hy0h0z1%28v=vs.110%29.aspx Другой альтернативой будет использование dynamic
,
Похоже, вы ссылались на сборку с типом Customer напрямую, а также пытались загрузить ее динамически, используя Assembly.LoadFile
, Я бы попробовал сделать что-то вроде этого, чтобы получить сборку и вызвать в ней методы:
Assembly asm = typeof(Customer).Assembly;
foreach (Type type in asm.GetTypes())
{
if (type.IsClass)
{
MethodInfo method = type.GetMethod(methodName);
// TODO: create obj
// TODO: create respar
method.Invoke(obj, respar);
}
}
Если вы настаиваете на динамической загрузке сборки и обращении к ней, вы должны понимать контексты привязки сборки, иначе вы столкнетесь с той же проблемой.
Контексты привязки сборки являются изолированными кэшами сборки в памяти. Load
(по умолчанию"), LoadFrom
, а также LoadFile
все используют разные контексты. Одни и те же типы из одной и той же сборки, загруженные в другом контексте, считаются разными во время выполнения. Когда ссылка на сборку загружена, она привязывается в контексте "Load" по умолчанию.
Другим вариантом может быть использование Assembly.Load
и укажите название сборки. Если сборка со строгим именем, другой вариант может быть Load
это раньше, а затем использовать LoadFrom
позже, потому что LoadFrom
проверит, была ли загружена сборка с таким именем Load
контекст перед загрузкой из указанного файла.