Garbage Collection e lo statement using

.::Home::.

.::Introduzione::.

1.Panoramica

4.DataBase

.::Presentazioni PPT::.

.::Link::.

.::DownLoad::.

 

Nota: si definisce scope (visibilità) di una variabile l'insieme delle parti di un programma da cui la variabile può essere usata.

Il .NET Framework utilizza un sistema chiamato reference-tracing garbage collection che periodicamente esegue tutti compiti necessari alla gestione della memoria.

Quando si creano oggetti che incapsulano risorse non gestite, bisogna esplicitamente rilasciarle quando non servono più all'applicazione.

Il tipo più comune di risorsa non gestita è un oggetto che ingloba una risorsa del sistema operativo, come un file, una finestra, o una connessione di rete. Nonostante il garbage collector sia in grado di tenere traccia della vita di un oggetto che incapsula una risorsa non gestita, non ha la conoscenza necessaria su come rimuovere dalla memoria la risorsa stessa. Per questo tipo di oggetto il Framework fornisce il metodo Object.Finalize che permette ad un oggetto di ripulire le sue risorse non gestite in maniera corretta quando il garbage collector reclama la memoria usata dall'oggetto.

Un oggetto può essere ripulito dalla memoria quando:

(A) Abbandona lo scope o il suo tempo vita è giunto al termine

(B) Nessuno fa più riferimento ad esso.

Non è possibile determinare quando il .NET Framework eseguirà il metodo Finalize per uno specifico oggetto. E' noto solo che il sistema chiamerà il metodo Finalize qualche tempo dopo che una delle due condizioni qui sopra si sarà verificata.

La Garbage Collection è vantaggiosa perché è automatica ma ha lo svantaggio di non poter essere inizializzata direttamente dalle applicazioni e alcune risorse possono rimanere attive per un tempo maggiore di quello che ci si aspetterebbe.

Una classe può gestire le risorse di sistema in un modo migliore se un distruttore aggiuntivo chiamato Dispose è implementato mediante l'interface IDisposable [vedi la sezione sulle interface per maggiori chiarimenti].

E' essenziale chiamare esplicitamente Dispose quando un oggetto non è più necessario. Il metodo Dispose rilascia tutte le risorse che possiede, chiamando il metodo GC.SuppressFinalize per l'oggetto che sta eliminado.

Se l'oggetto è già nella coda di terminazione (finalization queue) GC.SuppressFinalize evita che il suo metodo Finalize venga chiamato perché la sua esecuzione ha comunque un impatto negativo sulle prestazioni.

Oggetti con metodi Finalize hanno anche un costo di allocazione leggermente maggiore in quanto deve essere inserito un entry point aggiuntivo nella coda di terminazione.

Quindi se il metodo Dispose ha già compiuto il lavoro di ripulire l'oggetto, allora non sarà necessario la chiamata al metodo Finalize dell'oggetto da parte del Garbage Collector.

Lo statement using definisce uno scope alla fine del quale l'oggetto sarà rimosso dalla memoria.

Creando un'istanza di una classe dentro uno statement using ci si assicura che il metodo Dispose venga chiamato sull'oggetto all'uscita dallo statement, che può avvenire al termine dello statement o se viene rilevata una eccezione ed il controllo abbandona il blocco dello statement prima che questo sia terminato.

Sebbene lo statement using semplifichi il codice necessario a costruire e rimuovere un oggetto, si noti come sia utile soltanto per gli oggetti con un tempo vita non superiore a quello del metodo all'interno del quale sono costruiti.

Il codice che segue è d'esempio a quanto esposto qui sopra

using System;
public class Test : IDisposable
{
        //Constructor method per la classe
        public Test()
        {
          Console.WriteLine( "Calling the Constructor Method...." );
        } 
        //Finalization method per la classe
 ~Test()
        {
          Console.WriteLine( "Calling the Finalization Method...." );
        } 
 public void Hello()
 {
  Console.WriteLine( "Hello Everyone." );
 } 
        //Dispose method per la classe
 public void Dispose()
 {
  Console.WriteLine( "Calling the Dispose Method..." );
         //Supressing the Finalization method call
            GC.SuppressFinalize(this);
 }
} 
public class TestMain
{
 static public void Main()
 {
  
                using (Test t = new Test() )
  { 
   t.Hello();
  } 
 }
}  

 

Fonti:

Documentazione .NET Framework SDK

http://www.c-sharpcorner.com/Language/DiffUsingDirStmtYA.asp

.::^top^::.

(2002) A cura di Carlo Becchi