Удалить события, не зная их имен - PullRequest
4 голосов
/ 27 марта 2010

Возможно ли вместо этого:

person.Walking -= person_Walking1;
person.Walking -= person_Walking2;
person.Walking -= person_Walking3;

Сделайте это:

person.Walking = // remove all the handlers without knowing their names

Спасибо.

Ответы [ 4 ]

4 голосов
/ 27 марта 2010

Нет. Частью событий является то, что они мешают вам сделать это. Если я подписался на нажатие кнопки, а вы подписались на нажатие кнопки, какое право вы имеете на удаление моего обработчика? (Хорошо, это несколько антропоморфизирует, но вы поняли идею.) Обратите внимание, что дело не в том, чтобы знать «имя» обработчика событий - вы должны быть в состоянии предоставить ссылку на «равный» экземпляр делегата.

Например, если вы подписываетесь на событие, используя анонимный метод или лямбда-выражение, вам придется где-то хранить ссылку на него:

EventHandler handler = (sender, args) => Console.WriteLine("Clicked!");
button.Click += handler;
...
button.Click -= handler;

Когда вы используете имя метода, оно выполняет преобразование группы методов из имени метода в экземпляр делегата:

button.Click += HandleEvent;
...
button.Click -= HandleEvent;

Здесь задействованы два отдельных экземпляра делегата, но они равны, поскольку у них один и тот же список вызовов (они делают одно и то же), и у них одна и та же цель (они делают это "над" одним и тем же объектом ).

РЕДАКТИРОВАТЬ: я предполагаю, что вы только имеете доступ к нему как к событию, а не как поле - если вы пишете код в классе, который публикует событие, вы можете делать то, что вам нравится и установка поля в null (или удаление его из коллекции, или как ваша реализация работает) - это хорошо.

2 голосов
/ 27 марта 2010

Конечно. Просто установите:

person.Walking = null;
1 голос
/ 27 марта 2010

Это одна из причин, по которой были изобретены события. Если вы хотите сделать что-то подобное, используйте делегатов.

0 голосов
/ 27 марта 2010

Не извне класса, в котором определены события. Если бы вы действительно хотели, вы могли бы определить метод следующим образом:

public void ClearEventListeners() {
    MyEvent.Clear();
}

(Точный вызов может отличаться, если он существует, но IntelliSense должен указать вам правильное направление.)

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...