Garbage collection: differenze tra le versioni

Contenuto cancellato Contenuto aggiunto
Reference counting: Aggiunto il template "Vedi anche"
22denny91 (discussione | contributi)
mNessun oggetto della modifica
Riga 9:
# Recuperare le [[risorsa informatica|risorse]] utilizzate da questi oggetti.
 
Attuando il processo di ''garbage collection'', l'ambiente nel quale viene eseguito il programma gestisce la memoria automaticamente, liberando il [[programmatore]] dalla necessità di prevedere quando rilasciare le risorse utilizzate da un oggetto non più necessario all'[[elaborazione dati|elaborazione]]. Tale modalità automatica migliora la stabilità dei programmi in quanto consente di evitare quella classe di [[bug]] connessi all'utilizzo di puntatori alle varie aree di memoria già liberate in passato.<ref group="N">Tecnicamente chiamato il problema dei '[[dangling pointer]]s'.</ref>
 
Alcuni [[linguaggio di programmazione|linguaggi di programmazione]], come [[Java (linguaggio di programmazione)|Java]], [[Python]] e [[C sharp|C#]] ([[.NET]]), hanno un sistema di ''garbage collection'' integrato direttamente nell'ambiente di esecuzione, mentre per altri linguaggi, come il [[C (linguaggio)|C]] e il [[C++]], la sua eventuale implementazione è a carico del programmatore. Tuttavia molti linguaggi di programmazione utilizzano una combinazione dei due approcci, come [[Ada (linguaggio)|Ada]], [[Modula-3]] e [[Common Language Infrastructure|CLI]], consentonoconsentendo all'utente di eliminare manualmente gli oggetti, o, volendo velocizzare il processo, addirittura disattivare la gestione automatica del sistema GC. La garbage collection è quasi sempre strettamente integrata con l'[[Allocazione dinamica della memoria|allocazione di memoria]].
 
=== Benefici ===
 
La ''garbage collection'' esonera il programmatore dall'eseguire manualmente l'allocazione (richiesta) e la delocazionedeallocazione (rilascio) di aree di memoria, riducendo o eliminando del tutto alcune categorie di bug:
 
* ''[[Dangling pointer|Dangling pointers]]'': persistenza nel programma di puntatori che si riferiscono ad aree di memoria che contenevano oggetti, ormai delocatedeallocate. Utilizzare tali aree di memoria delocate può, nel migliore dei casi, provocare un errore fatale dell'applicazione, ma si possono manifestare altri problemi anche a distanza di tempo dalla effettiva delocazionedeallocazione. La risoluzione di questi problemi può essere molto difficoltosa.
* ''Doppia deallocazione'': il programma tenta di liberare nuovamente una zona di memoria già rilasciata.
* ''Alcuni tipi di [[memory leak]]s'': il programma perde traccia di alcune aree di memoria allocate<ref group="N">Ad esempio nel caso in cui il puntatore ad esse viene modificato.</ref>, perdendo la possibilità di deallocarle nel momento in cui non servono più. Questo tipo di problema può accumularsi nel corso dell'esecuzione del programma, portando, nel corso del tempo, all'esaurimento della memoria disponibile.
Riga 28:
 
* Consumo di risorse di calcolo: il processo consuma risorse di calcolo, al fine sia di tenere traccia dell'utilizzo delle varie aree di memoria, sia di poter decidere il momento e la quantità di memoria da liberare;
* Incertezza del momento in cui viene effettuata la Garbage Collection: Ilil momento in cui viene effettuata tale operazione non è prevedibile: e questa incertezza può determinare improvvisi blocchi o ritardi nell'esecuzione. Problemi di questo genere sono inaccettabili in ambienti [[sistema real-time|real-time]], nel rilevamento di [[driver|driver periferici]], e nell'[[transaction processing|elaborazione di transazioni]];
* Rilascio della memoria non deterministico: analogamente, sia il momento in cui una data area di memoria viene rilasciata, sia l'ordine di rilascio delle varie aree non più utilizzate, dipendono dal particolare [[algoritmo]] implementato dal ''garbage collector''. Si può dire che il rilascio di memoria avviene in modo non deterministico.
* Presenza di memory leak: i [[memory leak]], perdita o fuoriuscita di memoria, possono comunque verificarsi, nonostante la presenza di un Garbage Collector. Ciò può accadere se il programma mantiene un riferimento ad oggetti che hanno esaurito il loro ciclo logico di vita nell'applicazione. La presenza di riferimenti attivi comporta l'impossibilità da parte del collector di rilevare l'area di memoria come non utilizzata.<ref>{{cita pubblicazione |autore= Maebe Jonas |coautori= Ronsse Michiel, De Bosschere Koen|titolo=Precise detection of memory leaks|url=https://www.cs.virginia.edu/woda2004/papers/maebe.pdf|accesso=13 maggio 2010}}</ref> Questo può verificarsi, ad esempio, con collezioni di oggetti. Il monitoraggio del ciclo di vita degli oggetti è una responsabilità primaria dello sviluppatore in ambienti ''garbage-collected''.
 
== Tracing garbage collection ==
Riga 36:
 
=== Raggiungibilità di un oggetto ===
Siano "''p''" e "''q''" due oggetti, e sia q un oggetto raggiungibile. Diremo che p è raggiungibile in maniera ricorsiva, se e solo se esiste un riferimento ad esso tramite l'oggetto q (ovvero p è raggiungibile attraverso un oggetto q, a sua volta raggiungibile). Un oggetto può essere raggiungibile solo in due casi:
* Quando viene creato all'avvio del programma (oggetto globale) o di una sua sotto-procedura (oggetti di [[scope]], creati sullo [[Pila (informatica)|stack]]); l'oggetto in questione viene detto in tal caso radice;
* Quando un altro oggetto, raggiungibile, trattiene un riferimento ad esso; in modo più formale, la raggiungibilità è una ''chiusura transitiva''.
Riga 69:
==== Naïve mark-and-sweep ====
 
Nel ''mark-and-sweep'' ogni oggetto in memoria possiede un [[flag]], in genere è sufficiente un [[bit]], riservato esclusivamente per l'utilizzo del Garbage Collector. Quando l'oggetto viene creato, il [[flag]] viene posto in stato, ''flag clear''<ref name=":0" group="N">Trad.Ing.:"''Non in uso''"</ref>.
 
Durante la prima fase, o fase di Mark, del ciclo di Garbage Collection, viene scansionato l'intero set di [[Root (informatica)|root]], ponendo ogni oggetto in stato di ''flag set.''<ref name=":1" group="N">Trad.Ing.:"''In Uso''"</ref> Tutti gli oggetti accessibili dalla radice del set sono anch'essi contrassegnati come in stato di ''flag set''.<ref name=":1" group="N" />
 
Nella seconda fase, o fase di Sweep, ogni oggetto in memoria viene ancora una volta esaminato; quelli che hanno ancora il ''flag clear''<ref name=":0" group="N" /> non sono raggiungibili da nessun programma o dato, e la loro memoria viene quindi liberata. Per gli oggetti che sono marcati flag set, il flag viene posto in stato ''flag clear''<ref name=":0" group="N" />, preparandoli per il prossimo ciclo di Garbage Collection.
 
Questo metodo ha diversi svantaggi, per esempio, l'intero sistema viene sospeso durante la Garbage Collection in modo non sempre prevedibile e per periodi di tempo non determinabili a priori; questo tipo di comportamento può creare notevoli problemi in ambienti che necessitano di basse [[Latenza|latenze]] di risposta o in [[Sistema real-time|sistemi real-time]] o mission critical, con possibili malfunzionamenti, [[deadlock]], e arresti che possono compromettere l'intero sistema. Inoltre, tutta la memoria di lavoro deve essere esaminata, minimo due volte, causando potenzialmente problemi nei sistemi a [[memoria virtuale|memoria paginata]].
 
==== Tri-colour marking ====
A causa di questi svantaggi, gli algoritmi più moderni di ''garbage collection'' attuano delle varianti rispetto a semplici meccanismi, quali il ''mark-and-sweep'', applicando algoritmi del tipo ''tri-colour marking''. L'algoritmo effettua marcature su tre diversi livelli secondo le seguenti fasi:
 
# Crea set di livelli di bianco, grigio e nero utilizzati per segnare i vari progressi effettuati durante il ciclo.
Riga 103:
* Oggetti che fanno riferimento l'uno all'altro spesso possono essere spostati in locazioni di memoria adiacenti, aumentando la probabilità che questi si trovino sulla stessa linea della [[cache]] o della pagina di [[RAM|memoria virtuale]]. Questo accelererà notevolmente l'accesso ai nuovi oggetti attraverso i riferimenti.
 
Uno svantaggio del ''Garbage Collection in movimento'' è che consente l'accesso solo attraverso i riferimenti gestiti dai riferimenti dei rifiuti, impedendo l'[[aritmetica dei puntatori]]. Ciò accade perché i puntatori iniziali non sono più validi dal momento in cui il Garbage Collector sposta l'oggetto, diventeranno puntatori sospesi. Per l'[[interoperabilità]] con il [[codice nativo]], il Garbage Collector deve copiare la posizione dei contenuti dell'oggetto al di fuori della regione di memoria che contiene i rifiuti. Un approccio alternativo consiste nel salvare l'oggetto in memoria con un [[Codice PIN|codice pin]], impedendo al Garbage Collector di muoversi, consentendo ai puntatori nativi di lavorare direttamente con la memoria ed eventualmente consentendo l'aritmetica dei puntatori.<ref>{{Cita web
|url = https://msdn.microsoft.com/en-us/library/23acw07k.aspx
|titolo = Copying and Pinning