2009-05-28 19 views
7

Voglio invocare metodi con un determinato attributo. Quindi sto passando in rassegna tutti gli assembly e tutti i metodi per trovare i metodi con il mio attributo. Funziona bene, ma come faccio a richiamare un certo metodo quando ho solo il suo MethodInfo.Metodo di richiamo di 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 
     } 
    } 
} 

Il problema è che non conosco l'istanza della classe che contiene quel determinato metodo. Quindi non posso richiamarlo correttamente perché i metodi non sono statici. Voglio anche evitare di creare una nuova istanza di questa classe, se possibile.

risposta

5

Questo mi sembra un problema in termini di definizione del problema, piuttosto che codifica.

I metodi di istanza dipendono dall'istanza su cui sono chiamati - non ha senso chiamare un metodo di istanza senza preoccuparsi di come viene chiamato. (Come dice Martin, un metodo di istanza a cui non importa quale istanza viene chiamata dovrebbe essere quasi sempre statico. L'unica eccezione immediata che posso pensare è che i metodi virtuali, dove l'istanza specifica implicitamente quale implementazione usare).

Stabilire cosa è realmente significa che nel proprio contesto è che esiste un metodo di istanza annotato. Perché stai provando a invocare metodi comunque? Qual è l'immagine più grande? Che contesto hai? Sospetto fortemente che tu voglia una nozione di contesto: una raccolta di oggetti che puoi richiamare i metodi di istanza su.

+0

Quello che voglio fare è contrassegnare i metodi con un attributo personalizzato per renderli richiamabili da una linea di comando. Non importa dove siano. Ma sono d'accordo con te sul fatto che non ha senso invocare gli stessi metodi su istanze server in cui il metodo non è statico. Quindi lo userò in una sorta di classe manager che contiene una raccolta di questi oggetti per chiamare un richiamo su un'istanza specifica per parametri. Penso che questo farà quello che voglio. Grazie – apparat

11

I metodi non statici sono specifici dell'istanza, pertanto è necessario creare un'istanza della classe per richiamare il metodo. Se si ha la possibilità di cambiare il codice in cui è definito e il metodo non richiede di essere parte di un'istanza (non accede o modifica proprietà o metodi non statici all'interno della classe), la migliore pratica sarebbe sia per rendere comunque statico il metodo.

Supponendo che non si può fare statica allora il codice necessario è il seguente:

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

      MethodInfo[] methods = t.GetMethods(); 
      foreach (MethodInfo method in methods) 
      {      
       method.Invoke(instance, params...);  
      } 
    } 
+0

in realtà; I metodi non statici sono ** istanza ** specifici. i metodi statici sono specifici della classe. – Kris

+0

Whoops. Modificato - grazie. –

0

In realtà, penso che è necessario creare un elenco di oggetti esistenti e quindi cercare l'elenco. Quindi, quando crei questi oggetti invocabili, li memorizzerai nella lista (o forse la lista dovrebbe essere una lista di oggetti di qualche altro tipo che ha anche una descrizione dell'oggetto invokable). Quindi è possibile eseguire la scansione dell'elenco in fase di esecuzione, trovare quello che corrisponde al tipo di evento che si sta gestendo, quindi cercare il suo metodoInfo e chiamare .Invoke sulle informazioni sul metodo, assumendo ciò che si desidera fare. Dovresti anche passare gli argomenti appropriati, ma puoi farlo creando un vettore di oggetti dei tipi giusti.

Problemi correlati