Come scegliere tra diversi metodi di gestione / raccolta di eventi?

3

In situazioni in cui ho bisogno di scrivere codice osservatore / sottoscrittore, come scegliere tra i seguenti approcci?

A) Dichiarare un evento che notifica semplicemente un client qualcosa ma richiede che il client effettui una query per i dati, ad esempio

class SoothSayer{

    int DaysUntilApocalypse{get;}

    event EventHandler<EventArgs> TheEndIsNigh;

}

B) Dichiarazione di un evento con XXXEventArgs specifico contenente i dati dell'evento, ad es.

class SoothSayer{

    event EventHandler<ApocalypsePendingEventArgs> TheEndIsNigh
}

class ApocalypsePendingEventArgs:EventArgs{
    int DaysLeft{get;}
}

C) Utilizzo di una richiamata piuttosto che di un evento, ad es.

class SoothSayer{

    public SoothSayer(Action<int> endIsNighCallback){
        _endIsNightCallBack = endIsNighCallback;
    }
}
    
posta Grokodile 09.06.2011 - 00:38
fonte

3 risposte

5

La versione (c) è una forma di passaggio continuo , non è affatto un evento. È un metodo completamente diverso di flusso di controllo e può essere utilizzato per esprimere alcuni tipi complessi di flusso di controllo che sono difficili da esprimere con costrutti primitivi come loop e condizionali. Ad esempio, è la base per asincronia in C # 5 . Tutta la await lo fa, in sostanza, è una continuazione.

È certamente un costrutto valido, ma la risposta a quando si dovrebbe usare questo per la programmazione event-driven è mai , perché non è un evento. Non ci sono sottoscrizioni di alcun tipo; la richiamata è accoppiata alla chiamata al metodo. Inoltre, non puoi avere più abbonamenti, che puoi avere con qualsiasi vecchio event .

Quindi scende una scelta tra (a) usando un EventHandler o (b) semplice usando un MyEventHandler personalizzato con i dati di evento. E la risposta è semplice: usa un evento personalizzato se ci sono dati importanti, transitori associati all'evento.

Immagina di dover eseguire una query sulla posizione del cursore ogni volta che hai eseguito un gestore di eventi MouseDown . Sarebbe del tutto inaffidabile, perché la posizione del mouse potrebbe e spesso cambierebbe tra il momento in cui è stato sparato l'evento e il momento in cui è stato gestito. D'altra parte, un evento Initialized è piuttosto auto-esplicativo; succederà solo una volta nella vita di un oggetto e non c'è molto altro da dire al riguardo se non "OK, sono pronto!".

Quindi, in sintesi, (a) usa il EventHandler predefinito quando non hai nient'altro di interessante da dire, (b) usa un strong% tip_to% quando lo fai, e (c) non usa CPS per le notifiche degli eventi.

    
risposta data 09.06.2011 - 01:47
fonte
0

Suppongo che la domanda stessa abbia una risposta. Dipende dallo scenario.

Se intendi solo una notifica di una cosa particolare è successo e l'abbonato ha tutti i dati (o non richiede più dati dal publisher, per lo meno), quindi utilizza Metodo A

se vuoi passare alcuni dati che solo il publisher ha, anche ciò che è richiesto dal subcriber Usa Metodo B

Fornire qualche pseudo codice per uno scenario ipotetico:

 Class ClosedRoom
 {

      event: RoomOverHeatingHappened//notification
      event: RoomOptimalTemperatureReached//notification

      event: WindowOpenedOrClosed(int WindowNumber,Bool isOpened)//it notifies + tells which of the 4 windows got opened/closed + whether it is opened or closed

 }
    
risposta data 09.06.2011 - 08:39
fonte
0

Quindi la programmazione basata su eventi non è realmente messaggistica. I framework di messaggistica esistono all'interno di .NET, ma non sono molto abbondanti. La messaggistica normalmente porta al link degli attori . Gli attori sono un modo totalmente diverso di gestire i sistemi (e spesso rendono molto più semplice il software multi-thread) rispetto ad alcuni eventi di base.

link Quadro degli attori

link Axum è compilatore di attori con otturatore Microsoft

link Struttura di messaggistica / attore Sorta

    
risposta data 09.06.2011 - 21:51
fonte

Leggi altre domande sui tag