Frage

Ich habe einen Anwendungsfall, wo ich für eine Veranstaltung austragen muß. Aber vor dem Abbestellen i sicherstellen möchten, ob dieser Typ actully zu dieser Veranstaltung eingehängt ist oder nicht.

Bitte lassen Sie mich wissen, wie ich das erreichen kann?

War es hilfreich?

Lösung

Die Beispielklasse Publisher bietet eine Veranstaltung veröffentlichen. Event-Handler angebracht für die gegebene Klasseninstanz Die Methode isRegistered die Ereignisse abfragt und gibt true zurück, wenn es mindestens eine eingetragene / verknüpften Event-Handler von dieser Klasse Instanz ist. Die außer Kraft gesetzt isRegistered Methode macht die gleiche, aber für statische Typen.

Setzen Sie diesen Code in eine Konsolenanwendung Projekt und drücken Sie F5 zum Debuggen, es zu versuchen.

internal class Publisher
{
    internal event EventHandler<EventArgs> Publish;

    internal bool IsRegistered(Type type)
    {
        if (Publish == null) return false;
        //
        return (from item in Publish.GetInvocationList() where item.Target == null & item.Method.DeclaringType == type select item).Count() > 0;

    }
    internal bool IsRegistered(object instance)
    {
        if (Publish == null) return false;
        //
        return (from item in Publish.GetInvocationList() where item.Target == instance select item).Count() > 0;
    }

    static int Main(string[] args)
    {
        Publisher p = new Publisher();
        //
        p.Publish += new EventHandler<EventArgs>(static_Publish);
        p.Publish += new EventHandler<EventArgs>(p.instance_Publish);            
        //
        Console.WriteLine("eventhandler static_Publish attach: {0}", p.IsRegistered(typeof(Program)));
        Console.WriteLine("eventhandler instance_Publish attach: {0}", p.IsRegistered(program));
        //
        return 0;
    }

    void instance_Publish(object sender, EventArgs e)
    {

    }
    static void static_Publish(object sender, EventArgs e)
    {

    }
}`

Andere Tipps

Microsoft :

        // Wrap event invocations inside a protected virtual method
        // to allow derived classes to override the event invocation behavior
        protected virtual void OnRaiseCustomEvent(CustomEventArgs e)
        {
            // Make a temporary copy of the event to avoid possibility of
            // a race condition if the last subscriber unsubscribes
            // immediately after the null check and before the event is raised.
            EventHandler<CustomEventArgs> handler = RaiseCustomEvent;

            // Event will be null if there are no subscribers
            if (handler != null)
            {
                // Format the string to send inside the CustomEventArgs parameter
                e.Message += String.Format(" at {0}", DateTime.Now.ToString());

                // Use the () operator to raise the event.
                handler(this, e);
            }
        }

Sie suchen nach dem if (Handler! = Null) Teil. Es ist null , wenn es keine Abonnenten, nicht null , wenn es Abonnenten.

ein Pub / Sub-Umgebung unter der Annahme, rufen Sie einfach provider.Unsubscribe (Eventtype, Teilnehmer) und lassen Sie den Anbieter bestimmen, ob der Teilnehmer abonniert ist oder nicht

Es gibt zwei Möglichkeiten, wie Sie dies tun:

  1. Sie können einen neuen Delegaten Kette, mit dem Delegaten, der entfernt wird sein Abonnement kündigt, und vergleichen Sie dem von Ihnen bekam, bevor Sie es speichern. In dem Fall, in dem Sie einen Delegaten sind abzubestellen, dass hat abonniert haben, erhalten Sie einen neuen Delegaten Kette zurück, ohne dass die Delegierten. In dem Fall, in dem Sie versuchen, einen Delegaten abzumelden, dass hat nicht abonniert haben, erhalten Sie die gleiche Kette wie das zurückbekommen Sie hatten.
  2. Sie können manuell den Delegaten Kette gehen, um zu sehen, ob der Delegat Sie abbestellen möchten vorhanden ist. Dies kann mit den üblichen Methoden wie Linq .Contains der Einfachheit halber durchgeführt werden.

Der erste Fall kann wie der Code aussieht unten. Dadurch wird eine neue Delegierte Kette in einer temporären Variablen, mit den Delegierten Sie wollen entfernt, entfernt, erstellen und dann die temporäre Kette an die bestehenden Kette vergleichen. Wenn sie gleich sind, war der Delegierte nicht vorhanden.

private EventHandler _Changed;
public event EventHandler Changed
{
    add
    {
        _Changed += value;
    }
    remove
    {
        EventHandler temp = _Changed - value;
        if (_Changed == null || temp == _Changed)
            throw new InvalidOperationException(
                "Delegate is not subscribed, cannot unsubscribe");
        _Changed = temp;
    }
}

Die zweite wie der Code unten, wird dies einfach sehen, ob der Delegat Sie abbestellen möchten in der Kette der Teilnehmer vorhanden ist.

private EventHandler _Changed;
public event EventHandler Changed
{
    add
    {
        _Changed += value;
    }

    remove
    {
        if (_Changed == null || !_Changed.GetInvocationList().Contains(value))
            throw new InvalidOperationException(
                "Delegate is not subscribed, cannot unsubscribe");
        _Changed -= value;
    }
}

Beachten Sie, dass Sie können, wenn Sie wollen, einen ähnlichen Code verwenden, um den Fall zu behandeln, in denen ein Delegierter zweimal hinzugefügt wird.

Lizenziert unter: CC-BY-SA mit Zuschreibung
Nicht verbunden mit StackOverflow
scroll top