Вызвать метод по MethodInfo - PullRequest
7 голосов
/ 28 мая 2009

Я хочу вызывать методы с определенным атрибутом. Поэтому я перебираю все сборки и все методы, чтобы найти методы с моим атрибутом. Работает нормально, но как вызвать определенный метод, когда я получил только MethodInfo.

AppDomain app = AppDomain.CurrentDomain;
Assembly[] ass = app.GetAssemblies();
Type[] types;
foreach (Assembly a in ass)
{
    types = a.GetTypes();
    foreach (Type t in types)
    {
        MethodInfo[] methods = t.GetMethods();
        foreach (MethodInfo method in methods)
        {
            // Invoke a certain method
        }
    }
}

Проблема в том, что я не знаю экземпляр класса, который содержит этот определенный метод. Поэтому я не могу вызвать его правильно, потому что методы не являются статичными. Я также хочу по возможности избежать создания нового экземпляра этого класса.

Ответы [ 3 ]

11 голосов
/ 28 мая 2009

Нестатические методы зависят от конкретного экземпляра, поэтому вы должны создать экземпляр класса для вызова метода. Если у вас есть возможность изменить код, в котором он определен, и метод не требует, чтобы он был частью экземпляра (он не обращается к каким-либо нестатическим свойствам или методам внутри класса или не изменяет их), тогда передовая практика в любом случае сделать метод статичным.

Если вы не можете сделать его статичным, тогда код, который вам нужен, выглядит следующим образом:

    foreach (Type t in types)
    {
            object instance = Activator.CreateInstance(t);

            MethodInfo[] methods = t.GetMethods();
            foreach (MethodInfo method in methods)
            {                    
                method.Invoke(instance, params...);    
            }
    }
5 голосов
/ 28 мая 2009

Это кажется мне проблемой с точки зрения определения проблемы, а не кодирования.

Методы экземпляра зависят от того, к какому экземпляру они обращаются - нет смысла вызывать метод экземпляра, не заботясь о том, к чему он вызывается. (Как говорит Мартин, метод экземпляра, которому все равно, какой экземпляр вызывается, почти всегда должен быть статическим. Единственное непосредственное исключение, о котором я могу подумать, это виртуальные методы, где экземпляр неявно указывает, какую реализацию использовать.)

Подумайте, что на самом деле означает в вашем контексте, чтобы существовал аннотированный метод экземпляра. В любом случае, почему вы пытаетесь вызвать методы? Какая картина больше? Какой у вас контекст? Я сильно подозреваю, что вам понадобится какое-то понятие контекста - совокупность объектов, для которых вы можете вызывать методы экземпляра.

0 голосов
/ 17 марта 2012

На самом деле, я думаю, что вам нужно сделать, это создать список существующих объектов и затем выполнить поиск в списке. Поэтому, когда вы создаете эти вызываемые объекты, вы должны сохранять их в списке (или, возможно, список должен быть списком объектов какого-либо другого вида, который также имеет описание вызываемого объекта). Затем вы можете просмотреть список во время выполнения, найти тот, который соответствует типу события, которое вы обрабатываете, а затем найдите его methodInfo и вызвать .Invoke для информации о методе, предполагая, что это то, что вы хотите сделать. Вам также нужно будет передать соответствующие аргументы, но вы можете сделать это, создав вектор объектов правильных типов.

...