2010-11-19 3 views
4

Я читаю о деструкторах на C#, но у меня возникли проблемы с поиском приличного прецедента.Пример использования C# Destructor

Может ли кто-нибудь привести пример использования с объяснением?

Много, очень ценится.

Обновление
Пример кода в книге реализует одновременно Desctuctor и метод а Dispose(), см этот фрагмент кода из книги.

class MyClass 
{ 
    bool disposed = false; // Disposal status 
    public void Dispose() 
    { 
     Dispose(true); 
     GC.SuppressFinalize(this); 
    } 
    ~MyClass() 
    { 
     Dispose(false); 
    } 
    protected virtual void Dispose(bool disposing) 
    { 
     if (disposed == false) 
     { 
      if (disposing == true) 
      { 
       // Dispose the managed resources. Factored Dispose 

      } 
      // Dispose the unmanaged resources. 

     } 
     disposed = true; 
    } 
} 

Марко

+0

http://www.devx.com/dotnet/Article/33167/0/page/2 Довольно хорошая статья ... –

ответ

8

Финализаторы очень редко требуется сейчас. Они использовали, если у вас был прямой доступ к собственным ресурсам - но теперь вы обычно должны использовать SafeHandle.

Джо Даффи имеет excellent post about this, который идет в довольно больше деталей, чем я мог бы написать сам - так идите читать :)

Быстрое примечание по терминологии: версия ECMA в C# спецификации относится к ним как финализаторы; версия спецификации Microsoft всегда называла их деструкторами и продолжает делать это.

+0

Где вы сейчас? На поезде? = P Я прочитал ваше расписание, опубликованное на Meta. Я много рассмеялся, когда вы возвращались за своим расписанием! Hehehe ... Нет, я должен рассмотреть часовой пояс, поэтому вы должны быть дома, а не смотреть телевизор, но публиковать на SO! = P В любом случае! Приятного вечера! =) –

+0

@Will: чередование между публикацией и воспроизведением PixelJunk Monsters :) –

+0

какая блестящая статья - спасибо! Рад видеть, что мне редко придется использовать его благодаря внедрению SafeHandle. – Marko

2

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

+0

'Хотя иногда возникал вопрос о том, следует ли назвать десктурторы« деструкторами »или «финализаторы», спецификация языка C#, версия 3.0, выпущенная в конце 2007 года, называет этот метод деструктором. '- Apress Illustrated C# 2008. Сменилось ли это с тех пор? Кроме того, некоторый пример кода был бы фантастическим! – Marko

+0

Хорошо, проигнорируйте мой комментарий к примеру кода, похоже, что для этого очень редко используется! – Marko

0

Интерфейс IDisposable обеспечивает способ использования в качестве деструктора/финального набора.

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

+0

Я в порядке с downvotes, но, по крайней мере, скажите мне, что случилось, чтобы я мог узнать из моей ошибки, если ошибка есть! Даже Марк Байерс предлагает использовать интерфейс 'IDisposable'. –

+0

Нет, они совсем разные. 'Dispose' называется * явно * другим кодом, тогда как деструкторы/финализаторы вызываются сборщиком мусора, недетерминированно. –

+0

Hey Will: +1 для вас! Вы попали туда первым. – n8wrl

1

Финализаторы редко необходимы в C#, и добавление может привести к тому, что сборщик мусора займет больше времени, чтобы очистить мусор, поскольку для запуска финализатора требуется дополнительный проход. Вместо этого вы обычно должны использовать шаблон IDisposable.

Пример использования финализатора, если вы подозреваете утечку ресурсов, вы можете использовать его при отладке, чтобы проверить, правильно ли вызывается Dispose, прежде чем объект будет собран с мусором. Если объект, который содержит неуправляемые ресурсы, имеет свой финализатор, вызываемый до того, как Dispose был вызван, он может быть признаком утечки ресурсов. Но поскольку финализатор, возможно, никогда не будет называться, он не должен содержать критически важную логику приложения.

+0

Интересно, что код из книги, которую я читаю, реализует как Dispose, так и Destructor (который фактически вызывает Dispose (false) '). – Marko

+0

@Marko Этот шаблон был распространен перед введением 'SafeHandle' в .net 2.0.Сейчас это устарело. – CodesInChaos

+0

Спасибо вам обоим, я добавил пример кода из книги в качестве ссылки :) – Marko

1

Что вы подразумеваете под destructor? C# имеет

  • The IDisposable шаблон, который вы хотите использовать для детерминированного уничтожения
    Полезно, чтобы закрыть ручки, когда вы не нуждаетесь в них больше. Поэтому они закрыты сейчас, и не всякий раз, когда GC решает собрать объект, который может быть намного позже или совсем нет.
    Или в чистом управляемом коде, чтобы сообщить объекту удалить себя из графа объектов, отменить подписку на события, ...
    Обычно используется с оператором using
  • Завершение, которое практически бесполезно. Он работает в неизвестное время, он может не работать вообще, ...
    Единственное, что я использую для этого, это напомнить мне, что я забыл вызвать Dispose на что-то
    Хотя у него есть синтаксис деструктора C++ I не считайте это эквивалентом деструктора C++. Я предпочитаю думать о Dispose() как деструктор.
  • Critical finalization и SafeHandles, которые вы используете для родных ресурсов

Я думаю, что вместо шаблона вы публикуемую современный код должен владеть собственной SafeHandle и назвать это Dispose метод в его собственном Dispose.

0

У C# нет «деструкторов», поскольку вы, вероятно, думаете о них. С сборщиком мусора .NET коллекция объектов не произойдет сразу же, когда ваш класс выходит за рамки.

Я думаю, что вас больше интересует шаблон IDisposable. Это детерминированный способ очистить ресурсы, используемые вашим объектом.

Кроме того, классы .NET могут иметь «финализаторы», которые выполняются при сборке объекта. Его можно использовать для вызова, если исходный вызывающий объект игнорируется.

Но, реализуя финализатор в своих классах, он запускает специальную обработку для GC и может оказывать влияние на производительность.

Смежные вопросы