2010-07-11 3 views
5

ho questo tipo di codice:Come richiamare un evento automaticamente quando viene chiamata una funzione?

public class Foo 
{ 
    public SomeHandler OnBar; 

    public virtual void Bar() 
    { 
    } 
} 

Foo è una classe base e per dette altre classi potrebbe ereditare da essa.
Vorrei che l'evento OnBar venisse sempre attivato quando Bar() viene chiamato anche se non viene chiamato esplicitamente all'interno della barra.
Come può essere fatto?

risposta

9

Un modello comune consiste nell'avere un metodo non virtuale che eseguirà ciò che si desidera chiamando un metodo virtuale. Le sottoclassi possono sovrascrivere il metodo interno per modificare la funzionalità, ma il metodo pubblico può essere non virtuale sempre alzare prima l'evento.

public class Foo 
{ 
    public SomeHandler OnBar; 

    public void Bar() 
    { 
     if (OnBar != null) 
     { 
      OnBar(this, EventArgs.Empty); 
     } 
     BarImpl(); 
    } 

    protected virtual void BarImpl() 
    { 
    } 
} 
+0

Fondamentalmente un'implementazione del modello di metodo modello + 1 – DanP

+0

Quindi questo è il modo migliore? In C++ avrei usato bind() per creare una nuova funzione fuori dalla funzione di chiamata eventi e dalla funzione originale. –

2

Risposta breve: non è possibile. Non con ciò che Microsoft ti dà fuori dalla scatola.

Detto questo, date un'occhiata alla "programmazione orientata all'aspetto" in .NET. Google, potresti ottenere qualcosa di utile.

Aggiunto: Il modo standard sarebbe quello di aumentare l'evento nel metodo Bar() e quindi richiedere a tutte le classi derivate di chiamare l'implementazione di base. Ma non puoi applicarlo.

1

Prima di tutto il codice che hai fornito non verrà compilato.
Le funzioni virtuali devono avere un corpo.

Per garantire che l'evento venga attivato, è possibile fare qualcosa di simile.

public class Foo 
{ 
    public SomeHandler OnBar; 

    public void Bar() 
    { 
    OnBar(); (check for nulls) 
    ProtectedBar(); 
    } 

    protected virtual ProtectedBar() 
    { 
    } 
} 
+0

Sei corretto. Comunque non importa in questo caso. Era solo per dimostrare che la funzione può essere annullata. Non so perché sei stato downvoted. Ho upvoted per bilanciare. –

+1

Il codice che hai fornito non verrà compilato: la tua funzione virtuale non ha alcun tipo di reso e il tuo commento non è un commento. –

+0

Immagino che qualche collezionista di badge mi abbia messo in retata per un badge. :) –

0

Come ha detto Vilx-, Credo che il modo migliore per fare questo genere di cose è quello di utilizzare Aspect Oriented Programming.

Questo ti aiuterà con il "codice entangled" (cioè chiamando un evento in un metodo che non dovrebbe avere questa responsabilità) e "codice disperso" (cioè chiamando lo stesso evento in molti metodi, duplicando il tuo codice) problemi.

Si dovrebbe dare un'occhiata a postsharp, ha una versione gratuita della comunità.