Сравните действия делегатов

Не стесняйтесь сомневаться в моем здравом уме.

Мне нужно определить, есть ли Action vs ] Action - исходный экземпляр. У меня есть класс с переменной класса protected Action MessageCallback = null; когда мой абстрактный класс Message создается с помощью абстрактного метода, я заставляю «их» для инициализации MessageCallBack. Этот MessageCallback добавляется к IList > . Каждое действие, определенное в этом списке, может отличаться. Теперь я хочу удалить конкретное действие из списка, но мне не удается его сравнить.

Ниже приведен пример последней попытки настройки:

public void Unsubscribe<TMessage>(Action<TMessage> messageCallback)
    {
        var messageType = typeof(TMessage);

        var callbackTypes = messageReceivedCallbacks
            .Keys
            .Where(k => k.IsAssignableFrom(messageType));

        lock (messageReceivedCallbacks)
        {
            foreach (var callbackType in callbackTypes)
            {
                messageReceivedCallbacks[callbackType].Remove(new Action<object>(m => 
                    messageCallback((TMessage)m)));
            }
        }
    }

Я понимаю, что хочу сделать может быть невозможно, но обычно я просто делаю что-то неправильным образом или не имею надлежащих знаний, чтобы сделать это, как я полагаю. Заранее благодарим за любую помощь, которую вы оказываете.

      • ОБНОВЛЕНИЕ после попытки использования некоторых из приведенных ниже методов:

Их сравнение не работает. Ни одно из трех приведенных ниже предложений не работает. Я действительно считаю, что могу изменить то, как я справляюсь с этим, и заставить его работать так, как мне нужно, передав ключ с действием, которое затем указывает на отдельный список , а затем удалив его, показатель. Тем не менее, я чувствую, что мне все еще нужно приложить немало усилий для решения, поэтому я собираюсь дать немного больше информации, чтобы увидеть, поможет ли это.

Вот список:

private readonly IDictionary<Type, IList<Action<object>>> messageReceivedCallbacks;

Вот как добавляется действие к списку:

void AddMessageReceivedCallback<TMessage>(Action<TMessage> messageReceivedCallback)
    {
        var intermediateReceivedCallback = new Action<object>(m => 
            messageReceivedCallback((TMessage)m));

        var receivedList = messageReceivedCallbacks.GetOrCreateValue(typeof(TMessage),
            () => new List<Action<object>>());
        lock (receivedList)
        {
            receivedList.Add(intermediateReceivedCallback);
        }
    }

Потерпите меня, так как я новичок в этом более сложном кодировании. Я могу сказать, что это мешает мне выполнить прямое сравнение экземпляров из-за ключевого слова new . В попытке, которую я (впервые) опубликовал выше, я пытался добиться, чтобы мой обратный вызов соответствовал форме, в которой он был добавлен. Это не работает. Я пробовал сравнивать цели, методы и даже преобразовывать каждый из типов в другие, а затем сравнивать.

Я решил преобразовать переданный мной обратный вызов таким же образом, как он добавляется к последнему aka:

var callbackConverted = new Action<object>(m =>
                messageReceivedCallback((TMessage)m));

Затем я использовал немедленное окно, чтобы просто получить некоторую информацию (callback - это тот, который указан в списке, а callbackConverted - тот, который я передаю):

callback.Target
{MessageBus.MessageCoordinator.<Tests.MessageBus.TestMessage>}
    messageReceivedCallback: {Method = {Void <InitializeMessageCallback>b__0(Tests.MessageBus.TestMessage)}}

callback.Method
{Void <AddMessageReceivedCallback>b__8(System.Object)}
    [System.Reflection.RuntimeMethodInfo]: {Void <AddMessageReceivedCallback>b__8(System.Object)}
    base {System.Reflection.MethodBase}: {Void <AddMessageReceivedCallback>b__8(System.Object)}
    MemberType: Method
    ReturnParameter: {Void }
    ReturnType: {Name = "Void" FullName = "System.Void"}
    ReturnTypeCustomAttributes: {Void }


callbackConverted.Target
{MessageBus.MessageCoordinator.<Tests.MessageBus.TestMessage>}
    messageReceivedCallback: {Method = {Void <InitializeMessageCallback>b__0(Tests.MessageBus.TestMessage)}}
    messageType: {Name = "TestMessage" FullName = "Tests.MessageBus.TestMessage"}

callbackConverted.Method
    {Void <Unsubscribe>b__1d(System.Object)}
        [System.Reflection.RuntimeMethodInfo]: {Void <Unsubscribe>b__1d(System.Object)}
        base {System.Reflection.MethodBase}: {Void <Unsubscribe>b__1d(System.Object)}
        MemberType: Method
        ReturnParameter: {Void }
        ReturnType: {Name = "Void" FullName = "System.Void"}
        ReturnTypeCustomAttributes: {Void }

Я надеюсь, что эта дополнительная информация поможет.

      • ** UPDATE

Я понял что я делал это слишком сложным. Все, что мне нужно было сделать, это добавить мое действие, а затем удалить (единственный его экземпляр) из каждого словаря. Я старался изо всех сил сделать что-то сложное.

В настоящее время нет метода, который я могу сказать с уверенностью, но я отмечаю тот, который, как мне кажется, другие могли бы лучше всего использовать в качестве ответа. Спасибо всем, кто внес свой вклад.

10
задан Flimzy 29 May 2018 в 17:34
поделиться