Я построил систему событий, которая поддерживает dictionary
делегатов, добавляет/удаляет элементы к этим dictionary
с помощью общих методов подписки/отписки (каждый из которых выполняет действие type
T) и имеет метод публикации для уведомления подписчиков, когда что-то происходит. (который также принимает действие типа T). Все работает нормально, но я заметил, что не могу использовать += или -= при добавлении или удалении элементов в мой dictionary
, так как типы, переданные в методы (Action of T), не соответствуют типам, хранящимся в dictionary
(Delegate
). Следующий фрагмент показывает, что я могу и не могу делать.
private readonly Dictionary<Type, Delegate> delegates = new Dictionary<Type, Delegate>();
public void Subscribe<T>(Action<T> del)
{
if (delegates.ContainsKey(typeof(T)))
{
// This doesn't work!
delegates[typeof(T)] += del as Delegate;
// This doesn't work!
delegates[typeof(T)] += del;
// This is ok
delegates[typeof(T)] = (Action<T>)delegates[typeof(T)] + del;
// This is ok
var newDel = (Action<T>)delegates[typeof(T)] + del;
delegates[typeof(T)] = newDel;
// This is ok
del += (Action<T>)delegates[typeof(T)];
delegates[typeof(T)] = del;
// This is ok
delegates[typeof(T)] = Delegate.Combine(delegates[typeof(T)], del);
}
else
{
delegates[typeof(T)] = del;
}
}
Я в основном понимаю ответ Джона Скита здесь += operator for Delegate, в частности, эта часть
Двоичный оператор + выполняет комбинацию делегатов, когда оба операнда относятся к некоторому типу делегата D. (Если операнды имеют разные типы делегата, возникает ошибка времени связывания.)
Чего я не понимаю, так это
Компилятор превращает его в вызов Delegate.Combine
. Обратная операция с использованием - или -= использует Delegate.Remove
.
Что именно происходит, когда я использую += или -= вместо Delegate.Combine
? Каковы различия между ними, делающие одну реализацию действительной, а другую недействительной?
Delegate.Combine
. У него недостаточно информации, основанной на объявленном типеdelegates
, чтобы принять это решение. - person Damien_The_Unbeliever   schedule 11.04.2019