Flexible Delegates

In den meisten C#-Programmen dürften Delegates nur vorkommen, um sie einem Event anzuhängen. Es könnte deshalb der Eindruck entstehen, Delegates seien unwichtig und ausser im Zusammenhang mit Events für sich alleine nicht zu gebrauchen. Einige Tests, die ich kürzlich durchgeführt habe, zeigen aber ein anderes Bild.

Anlass war folgende Frage: Hängen an einem Event mehrere Handler, hat man so gut wie keine Kontrolle darüber, in welcher Reihenfolge diese aufgerufen werden. Was tut man, wenn das ein Problem darstellt, d.h. wenn man die Kontrolle über die Aufruf-Reihenfolge benötigt?

Eine mögliche Antwort ist die folgende: Man lässt Events links liegen und arbeitet direkt mit Delegates.

Delegates haben gegenüber anderen .NET-Objekten eine „magische“ Eigenschaft: Man kann sie aufrufen, d.h. man kann mit ihrer Hilfe Methoden bestimmter Objekte ausführen. Sie sind aber trotzdem ganz normale Objekte, und man kann mit ihnen alles machen, was man mit anderen Objekten auch machen kann, inklusive Verwendung für Template-basierte Klassen wie List<T>. Wie untenstehender Demo-Code zeigt, ist es deshalb kein Problem, eine Art Event in Form einer Liste selbst mit sehr wenig Aufwand nachzubauen, einer Liste, wo man dann eben selbst beliebig bestimmen kann, in welcher Reihenfolge welcher Delegate aufgerufen werden soll.

Delegates sind übrigens Objekte der Klasse Delegate. Objekte dieser Klasse haben eine öffentliche Eigenschaft Target – das Objekt, dessen Methode sie aufrufen. Wenn man will, kann man also sogar noch weiter gehen als einfach die Reihenfolge des Aufrufs kontrollieren und z.B. einen Aufruf nur durchführen, wenn sich das entsprechende Objekt in einem bestimmten Zustand befindet.

using System.Collections.Generic;

namespace DelegateDemo {
  delegate void Method(int firstArg, int secondArg);

  class TestClass {
    public void TestMethod(int x, int y) {
    }
  }

  class Program {
    static void Main(string[] args) {
      TestClass a = new TestClass();
      TestClass b = new TestClass();
      TestClass c = new TestClass();

      List<Method> methods=new List<Method>();
      methods.Add(a.TestMethod);
      methods.Add(b.TestMethod);
      methods.Add(c.TestMethod);

      methods[0](0, 1);
      methods[1](2, 3);
      methods[2](4, 5);
    }
  }
}
Veröffentlicht in Keine Kategorie. Schlagwörter: , , . Leave a Comment »

Schreibe einen Kommentar

Trage deine Daten unten ein oder klicke ein Icon um dich einzuloggen:

WordPress.com-Logo

Du kommentierst mit Deinem WordPress.com-Konto. Abmelden / Ändern )

Twitter-Bild

Du kommentierst mit Deinem Twitter-Konto. Abmelden / Ändern )

Facebook-Foto

Du kommentierst mit Deinem Facebook-Konto. Abmelden / Ändern )

Google+ Foto

Du kommentierst mit Deinem Google+-Konto. Abmelden / Ändern )

Verbinde mit %s

%d Bloggern gefällt das: