2012-03-24 12 views
3

Angenommen, ich habe eine Basisklasse namens IMessage und viele abgeleitete Nachrichtenklassen.Wie rufe ich verschiedene Methoden für verschiedene Klassen-Typen in einem generischen Nachrichtenempfänger auf?

In meinem Programm habe ich eine Methode, die alle Nachrichten empfängt:

void ReceiveMessage(IMessage message) 
{ 
} 

und ich möchte für jede Art von Nachricht, die eine spezifische Methode aufzurufen. Es wäre toll, wenn ich tun kann:

void ReceiveMessage(IMessage message) 
{ 
    HandleMessage(message); 
} 

void HandleMessage(DummyMessage message) 
{ 
    Blah; 
} 

void HandleMessage(SillyMessage message) 
{ 
    Yuk; 
} 

..aber scheinbar „wir gehen nicht aus, wie die“.

Wie also würde ich spezifische Handler für bestimmte Nachrichten implementieren, die von einem einzigen Message-Handler aus aufgerufen werden?

+1

Sollte nicht die IMessage-Schnittstelle die ‚gemeinsame‘ Methode (n) definieren, die alle Implementierungen von IMessage implementieren, die erlauben würde, Sie diese Methoden nur in Ihrer ReceiveMessage-Methode aufrufen? –

+0

@TrevorPilley Kommt drauf an. Es gibt Zeiten, in denen das nicht angebracht ist. Viele Spiele-Engines oder 3D-Szenendiagramme haben beispielsweise Situationen, in denen jeder Szenentyp (Nachricht) von verschiedenen "Darstellern" innerhalb der Szene sehr unterschiedlich gehandhabt wird. –

+0

Ich möchte, dass der Handler in einer anderen Klasse aufgerufen wird, nicht in der Nachricht selbst ... (Zum Beispiel würde eine Serverklasse alle Handler für verschiedene Nachrichten enthalten.) – Pygmy

Antwort

4

Der klassische Weg, diese Art zu handhaben von Situation ist über die Visitor pattern.

aber sagte, dass Sie kann dies tatsächlich behandelt ein bisschen leichter in C# über dynamic, etwa so:

void ReceiveMessage(IMessage message) 
{ 
    dynamic specificMessage = message; 
    this.HandleMessage(specificMessage): 
} 

Die dynamische Bindungsmodul finden, zur Laufzeit, das „beste“ Spiel für Ihre spezifische Botschaft Geben Sie den Anruf ein und leiten Sie ihn an die entsprechende Methode weiter.

+0

Danke, zum Glück habe ich Targeting .net 4.0 so dynamisch spart den Tag! \ o / – Pygmy

0

Versuchen Sie es mit einer Factory-Methode. Fabrik-Design-Muster nachschlagen.

1

Ihre IMessage-Schnittstelle sollte eine Handle() Funktion definiert haben, dass jeder Typ implementiert:

public interface IMessage 
{ 
    void HandleMessage(); 
} 

public class DummyMessage : IMessage 
{ 
    public void HandleMessage() 
    { 
     Blah; 
    } 
} 

public class SillyMessage : IMessage 
{ 
    public void HandleMessage() 
    { 
     Yak; 
    } 
} 

Dann sind Sie es so nennen würde:

void ReceiveMessage(IMessage message) 
{ 
    message.HandleMessage(); 
} 
+0

Dies funktioniert nicht, wenn mehrere Empfänger dies tun müssen Behandeln Sie einzelne Nachrichtentypen unterschiedlich. Das Visitor-Muster ist in diesem Fall der klassische Weg, um mit diesem Szenario umzugehen. –

0

Es ist möglich zu tun, was Sie vorschlagen, obwohl es nicht sehr trocken ist, und ich denke, die anderen Vorschläge sind hier angemessener. Dennoch hier im Interesse der Vollständigkeit, ist ein Ansatz nahe, was Sie ursprünglich suchten:

void ReceiveMessage(IMessage message) { 
    if(message as DummyMessage != null) HandleMessage(message as DummyMessage); 
    else if(message as SillyMessage != null) HandleMessage(message as SillyMessage); 
    // etc 
} 
Verwandte Themen