Как полностью удалить все элементы для статического события - PullRequest
2 голосов
/ 19 ноября 2011

У меня есть класс Plotter, в котором есть статическое событие (объявлено public static event MouseEventHandler MultiCursorMouseMove для тех, кто интересуется, как у меня статическое событие).

Он имитирует графический график, и наше текущее приложение отображает около 30-40 из них. Цель события - нарисовать курсор на всех отображаемых графиках, чтобы указать значение для графика в тот момент, когда на него указывает курсор мыши.

Проблема, с которой я сталкиваюсь, заключается в том, что экземпляры Plotter имеют это статическое событие и отказываются умирать. Насколько я могу судить, глядя на них в профилировщике памяти, каждый экземпляр Plotter (а также содержащая их форма) хранится в памяти с помощью EventHandler, привязанного к этому событию MultiCursorMouseMove. Я закодировал установку, которая запускает метод Dispose для каждого из Plotter экземпляров, который включает удаление делегата из MultiCursorMouseMove, но, похоже, он не приносит никакой пользы. Согласно тому, что я вижу через отладчик, Plotter.MultiCursorMouseMove регистрируется как ноль, но эти экземпляры все еще не собираются и, как я могу сказать через профилировщик, все экземпляры продолжают существовать из-за MultiCursorMouseMove.

Итак, у меня вопрос: есть ли способ явно заявить «удалить всех делегатов, связанных с этим событием»?
Я думаю, что таким образом я буду уверен, что избавился от всех них, не говоря уже о том, что это упростит вещи по сравнению с моим текущим кодом, который во время метода Dispose циклически перебирает все элементы управления на вкладке и запускает Dispose на всех Plotter найденных объектах.

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

Ответы [ 2 ]

1 голос
/ 19 ноября 2011

Вы можете расширить синтаксис вашего события, чтобы отслеживать добавление / удаление вызовов, чтобы найти те объекты, которые не отписались:

public static event MouseEventHandler MultiCursorMouseMove 
{
  add 
  {
  }
  remove
  {
  }
}

Вы также можете следовать Слабый шаблон событий ,или , описанный Дж. Рихтером .Слабые обработчики основаны на слабых ссылках, которые не блокируют GC.

И, наконец, вы можете использовать жесткий подход Reflection для очистки массива делегатов в статическом объекте MouseEventHandler.

1 голос
/ 19 ноября 2011

Итак, у меня вопрос, есть ли способ явно заявить msgstr "удалить всех делегатов, связанных с этим событием"?

Вы пытались явно установить "MultiCursorMouseMove" в ноль?

...