Какова цель реализации интерфейса IDisposable? - PullRequest
4 голосов
/ 18 января 2009

Какова цель реализации интерфейса IDisposable? Я видел, как некоторые классы реализуют это, и я не понимаю, почему.

Ответы [ 5 ]

9 голосов
/ 18 января 2009

Если ваш класс создает неуправляемые ресурсы, вы можете реализовать IDisposable, чтобы эти ресурсы были должным образом очищены при удалении объекта. Вы переопределяете Dispose и отпускаете их там.

5 голосов
/ 18 января 2009

Когда ваши классы используют какой-то системный ресурс, ответственность за обеспечение освобождения ресурса также лежит на классе. При разработке .Net вы должны делать это в методе Dispose класса. Интерфейс IDisposable отмечает, что вашему классу необходимо освободить ресурс, когда он больше не используется, а метод Dispose доступен, чтобы пользователи вашего класса могли вызывать его для освобождения потребляемых ресурсов.

Метод IDisposable также необходим, если вы хотите, чтобы автоматическая очистка работала правильно, и хотите использовать оператор using ().

3 голосов
/ 18 января 2009

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

using(Timer tmr=new Timer("blah"))
{
    // do whatever
}

Конечно, это можно сделать вручную, но я чувствую, что нужно по возможности использовать возможность компилятора автоматически генерировать правильный код.

2 голосов
/ 18 января 2009

Все это связано с механизмом сбора мусора. Крис Селлс описывает сборку мусора, финализаторы и причину шаблона Dispose (и интерфейса IDisposable) эпизод 10 .NET Rocks! (начиная примерно через 34 минуты).

1 голос
/ 16 апреля 2011

Многие объекты манипулируют другими объектами так, что если их не очистить, это вызовет проблемы. Эти другие объекты могут быть почти чем угодно, и они могут быть почти где угодно. Например, объект Socket может попросить другую машину открыть TCP-соединение. Эта другая машина может быть не в состоянии обрабатывать очень много соединений одновременно; действительно, это может быть устройство, оснащенное Интернетом, которое может обрабатывать только одно соединение за раз. Если бы программа открыла сокет и просто забыла об этом, никакой другой компьютер не смог бы подключиться к устройству, если только или до тех пор, пока сокет не будет закрыт (возможно, устройство может закрыть сам сокет после нескольких минут бездействия, но это будет бесполезен до тех пор).

Если объект реализует IDisposable, это означает, что он обладает знаниями и стимулом, необходимыми для выполнения необходимых действий по очистке, и такие действия необходимо выполнить до того, как такие знания и импульс будут потеряны. Вызов IDisposable.Dispose обеспечит выполнение всех таких действий по очистке, после чего объект можно будет безопасно покинуть.

Microsoft разрешает объектам запрашивать защиту от отказа, регистрируя метод Finalize. Если объект делает это, метод Finalize будет вызван, если система обнаружит, что объект был оставлен. Ни объект, ни любые объекты, на которые он имеет прямые или косвенные ссылки, не будут удалены из памяти до тех пор, пока метод Finalize не получит возможность запуска. Это обеспечивает что-то вроде «обратного останова» в случае, если объект был оставлен без предварительной утилизации. Однако существует множество ловушек с объектами, которые реализуют Finalize, поскольку нет никакой гарантии относительно того, когда он будет вызван. Мало того, что объект может быть заброшен задолго до вызова Finalize, но и если вы не будете осторожны, система может вызвать Finalize объекта, пока его часть еще используется. Опасные вещи. Гораздо лучше правильно утилизировать.

...