Метод продления автоматического удаления разумно? - PullRequest
4 голосов
/ 08 октября 2010

Я писал некоторые пользовательские элементы управления WinForm, которые выполняют довольно много рисования и, следовательно, имеют тенденцию иметь много одноразовых графических полей, лежащих вокруг (кисти, ручки, растровые изображения и т. Д.), И в результате мои элементы управленияМетод Dispose () должен вызывать Dispose для каждого из них.

Я обеспокоен тем, что я (или будущий сопровождающий) мог легко пропустить поле, которое необходимо удалить, либо забыв удалить его, либо непонимая, что он реализует IDisposable.Таким образом, я написал очень простой метод расширения для Object, который находит все поля IDisposable и удаляет их:

static public void DisposeAll(this Object obj)
{
   var disposable = obj.GetType()
                       .GetFields(BindingFlags.NonPublic | BindingFlags.Public | BindingFlags.Instance)
                       .Select(fi => fi.GetValue(obj))
                       .Where(o => o != null && o is IDisposable)
                       .Cast<IDisposable>();

   foreach (var d in disposable) d.Dispose();
}

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

Ответы [ 5 ]

4 голосов
/ 08 октября 2010

Обычно вы не хотите выбрасывать всех одноразовых участников. Например. ссылка на родительскую форму.

2 голосов
/ 08 октября 2010

Нет, это не очень хороший подход.Рисованные объекты, которые вы создаете в методе OnPaint, всегда должны быть локальными переменными, заключенными в , используя оператор Ваш подход требует объявления класса, просто для хранения этих объектов.Больно и неэффективно.Кроме того, вы будете располагать объектами, которые никогда не следует выбрасывать.Как и сборные ручки и кисти, например, Pens.Black.

1 голос
/ 08 октября 2010

Трудно сказать, сработает ли это для вашего конкретного случая; Я вижу наибольшую проблему в порядке Dispose() вызовов. Если одна неуправляемая ручка зависит от другой, у вас будут странные проблемы с рисованием, памятью и т. Д.

ИМХО.

0 голосов
/ 08 октября 2010

Можно использовать FxCop или Анализ кода (Visual Studio 2010 Premium или выше).

Правило CA2213 будет искать поля, которыеВы забыли избавиться.

0 голосов
/ 08 октября 2010

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

Автоматизация хороша для объектов, в которых вы уверены, что они вообще не будут возвращены.

...