Версия для печати темы
Нажмите сюда для просмотра этой темы в оригинальном формате
Форум программистов > Общие вопросы по .NET и C# > Как вызвать функцию используя invoke


Автор: dimonpage1 31.10.2007, 09:20
Доброе утро, есть Dll которая содержит в себе функцию типа List<string>.
из проекта пытаюсь вызвать функцию из dll, но выдает ошибку "Cannot implicitly convert type 'object' to 'System.Collections.Generic.List<string>'."
я понимаю, что компилятор не может конвертировать эти типы.
Но как мне вызвать функцию, может подскажете?

Код

Assembly AccountPC_Load = Assembly.LoadFile("AccountPC.dll");
Type AccountPC_TypeGetInfo = AccountPC_Load.GetType("AccountPC.frmTemp");
object AccountPC_InstGetInfo = Activator.CreateInstance(AccountPC_TypeGetInfo);
MethodInfo meth = AccountPC_TypeGetInfo.GetMethod("GetFormInfo");

List<string> res = new List<string>();

res = meth.Invoke(AccountPC_Inst,null);

Автор: tol05 31.10.2007, 10:08
Цитата(dimonpage1 @  31.10.2007,  09:20 Найти цитируемый пост)
я понимаю, что компилятор не может конвертировать эти типы.

Способы конвертирования типов знаешь? Я пользуюсь этим:
Код

List<string> res = meth.Invoke(AccountPC_Inst,null)  as List<string>;

Автор: Wizard_Memfis 31.10.2007, 10:18
Ну или просто вот так:
Код

List<string> res = (List<string>)meth.Invoke(AccountPC_Inst,null);

Если конечно уверен что возвращает именно этот объект!
Ну а вообще согласен с tol05, проверять все-равно надо полученный объект! smile 
Ну я бы еще вот это добавил:
Код

Assembly AccountPC_Load = Assembly.LoadFile("AccountPC.dll");
Type AccountPC_TypeGetInfo = AccountPC_Load.GetType("AccountPC.frmTemp");
object AccountPC_InstGetInfo = Activator.CreateInstance(AccountPC_TypeGetInfo);
MethodInfo meth = AccountPC_TypeGetInfo.GetMethod("GetFormInfo");
if(meth==null)
{
// в зависимости от проги либо эксепшен бросал или в лог писал!
log.Warn("Can't access GetFormInfo method!");
throw new EXception("Can't access GetFormInfo method!");
}
List<string> res = (List<string>) meth.Invoke(AccountPC_Inst,null);

А дальше уже res проверять! smile 

Автор: tol05 31.10.2007, 10:26
Wizard_Memfis, ну если проверять, так уж все до конца проверять.  smile
Цитата(Wizard_Memfis @  31.10.2007,  10:18 Найти цитируемый пост)
List<string> res = (List<string>) meth.Invoke(AccountPC_Inst,null);

этот способ выбросит Exception, если возвращаемый тип не приведется к List<string> (а в моем способе ссылка просто будет равна null). В твоем случае нужно писать
Код

try
{
   List<string> res = (List<string>) meth.Invoke(AccountPC_Inst,null);
}
catch(InvalidCastException ex){}




Автор: dimonpage1 31.10.2007, 10:29
и тем и тем способом пробовал, но выдает в ходе исполнения программы
Object does not match target type.
что это может быть?

Автор: Wizard_Memfis 31.10.2007, 10:31
Согласен tol05, тупанул!Ну тут и спорить нечего, потому что твой способ- это классика хорошего кода! smile

Добавлено через 2 минуты и 1 секунду
А на 
Цитата

и тем и тем способом пробовал, но выдает в ходе исполнения программы
Object does not match target type.
что это может быть?

Все таки функция возвращает не этот тип!Проверь и продебаж!Главное. посмотри что находится в MethodInfo meth, та ли функция которая тебе нада!

Автор: dimonpage1 31.10.2007, 10:48
сори я static забыл

Автор: dimonpage1 31.10.2007, 11:06
может лучше будет читать из dll глобальную переменную?
public string TEST = "test"
но только я незнаю, как можно получить значение переменной, подскажите?

Автор: Wizard_Memfis 31.10.2007, 11:21
Аналогично:
Код

Assembly AccountPC_Load = Assembly.LoadFile("AccountPC.dll");
Type AccountPC_TypeGetInfo = AccountPC_Load.GetType("AccountPC.frmTemp");
object AccountPC_InstGetInfo = Activator.CreateInstance(AccountPC_TypeGetInfo);
FieldInfo field = AccountPC_TypeGetInfo.GetField("GetFormInfo");
if(field ==null)
{
// в зависимости от проги либо эксепшен бросал или в лог писал!
log.Warn("Can't access GetFormInfo method!");
throw new EXception("Can't access GetFormInfo method!");
}
// Установить значение
object value = "test";
field .SetValue(AccountPC_Load, value); // вот тут мог ошибиться с типом вызывающего объекта 
// AccountPC_Load вообщем тут должен стоять объект, переменную которого ты вызываешь!

// Прочитьтать занчение
field.GetValue(AccountPC_Load);

 smile 

Автор: tol05 31.10.2007, 11:40
Цитата(Wizard_Memfis @  31.10.2007,  10:31 Найти цитируемый пост)
Согласен tol05, тупанул!Ну тут и спорить нечего, потому что твой способ- это классика хорошего кода!

Но-но, я попросил бы ... не материться...  smile 
dimonpage1, не только сообщение об ошибке давай, но и строку, где она возникает.


Цитата(dimonpage1 @  31.10.2007,  10:48 Найти цитируемый пост)
сори я static забыл

Вызывай через Type.InvokeMember().  Activator.CreateInstance не нужен, причем тут создание инстанса, если статический член типа используется

Автор: dimonpage1 1.11.2007, 08:50
tol05, это интересно, а можно примерчик под мой случай подкинуть? smile

Автор: tol05 1.11.2007, 10:41
Код

namespace AccountPC
{
    public class frmTemp
    {
        public static List<string> GetStaticFormInfo()
        {
            return new List<string>(new string[]{"static"});
        }

        public List<string> GetFormInfo()
        {
            return new List<string>(new string[]{"instance"});
        }
    }
}


Код

Assembly AccountPC_Load = Assembly.LoadFile("AccountPC.dll");
Type AccountPC_TypeGetInfo = AccountPC_Load.GetType("AccountPC.frmTemp");
//вызов метода экземпляра
object AccountPC_InstGetInfo = Activator.CreateInstance(AccountPC_TypeGetInfo);
MethodInfo meth = AccountPC_TypeGetInfo.GetMethod("GetFormInfo");
List<string> res = meth.Invoke(AccountPC_InstGetInfo, null) as List<string>;

//вызов статического метода
List<string> resStatic = AccountPC_TypeGetInfo.InvokeMember("GetStaticFormInfo", BindingFlags.Static | BindingFlags.InvokeMethod | BindingFlags.Public, null, null, null) as List<string>;

//или так
MethodInfo meth2 = AccountPC_TypeGetInfo.GetMethod("GetStaticFormInfo");
List<string> resStatic2 = meth2.Invoke(null, null) as List<string>;


Powered by Invision Power Board (http://www.invisionboard.com)
© Invision Power Services (http://www.invisionpower.com)