Limpando recursos não gerenciados

Para a maioria dos objetos que o aplicativo cria, você pode confiar no coletor de lixo do .NET para lidar com o gerenciamento de memória. No entanto, ao criar objetos que incluem recursos não gerenciados, você deve liberar explicitamente esses recursos quando terminar de usá-los. Os tipos mais comuns de recursos não gerenciados são objetos que agrupam recursos do sistema operacional como arquivos, janelas, conexões de rede ou conexões de banco de dados. Embora o coletor de lixo consiga controlar o tempo de vida de um objeto que encapsula um recurso não gerenciado, ele não sabe como liberar e limpar o recurso não gerenciado.

Se seus tipos usam recursos não gerenciados, você deve fazer o seguinte:

  • Implementar o padrão de descarte. Isso exige que você forneça uma implementação IDisposable.Dispose para habilitar a liberação determinística de recursos não gerenciados. Um consumidor do seu tipo chamará Dispose quando o objeto (e os recursos que ele usa) não forem mais necessários. O método Dispose libera imediatamente os recursos não gerenciados.

  • Caso um consumidor do seu tipo esqueça de chamar Dispose, forneça uma maneira de liberar os recursos não gerenciados. Há duas maneiras de fazer isso:

    • Usar um identificador seguro para encapsular o recurso não gerenciado. Essa é a técnica recomendada. Os identificadores seguros são derivados da classe abstrata System.Runtime.InteropServices.SafeHandle e incluem um método Finalize robusto. Ao usar um identificador seguro, você simplesmente implementa a interface IDisposable e chama o método Dispose do seu identificador seguro em sua implementação do IDisposable.Dispose. O finalizador do identificador seguro é chamado automaticamente pelo coletor de lixo quando seu método Dispose não é chamado.

      ou

    • Defina um finalizador. A finalização habilita a liberação não determinística de recursos não gerenciados quando o consumidor de um tipo não chama IDisposable.Dispose para fazer o descarte de forma determinística.

      Aviso

      A finalização do objeto pode ser uma operação complexa e propensa a erros, recomendamos que você use um identificador seguro em vez de fornecer seu próprio finalizador.

Os consumidores do seu tipo poderão então chamar sua implementação de IDisposable.Dispose diretamente para liberar a memória usada pelos recursos não gerenciados. Quando você implementa corretamente um método Dispose, o método Finalize do seu identificador seguro ou sua própria substituição do método Object.Finalize torna-se uma proteção para limpar recursos para o caso do método Dispose não ser chamado.

Nesta seção

A implementação de um método Dispose descreve como implementar o padrão de descarte para liberar recursos não gerenciados.

Usar objetos que implementam IDisposable descreve como os consumidores de um tipo garantem que a implementação Dispose seja chamada. É altamente recomendável usar a instrução C# using (ou Visual Basic Using) para fazer isso.

Referência

Tipo/Membro Descrição
System.IDisposable Define o método Dispose para liberar recursos não gerenciados.
Object.Finalize Cuida da finalização de objetos quando os recursos não gerenciados não são liberados pelo método Dispose.
GC.SuppressFinalize Suprime a finalização. Este método geralmente é chamado de um método Dispose para impedir a execução de um finalizador.