2012-01-25 17 views
14

Garbage ho il seguente codice:nuova discussione() e Collezione

new Thread(new ThreadStart(delegate() 
{ 
    while (true) 
    { 
     //something 
    } 
})).Start(); 

Può garbage collector finalizzare questa istanza di Thread mentre è in stato Running?

risposta

21

Il CLR tiene traccia di tutti i thread in esecuzione. Finché ci sono riferimenti agli oggetti, questi non saranno raccolti. E poiché CLR mantiene un riferimento a tutti i thread in esecuzione, il GC non li toccherà.

13

No; i thread in esecuzione contano come radici. Non verrà raccolto un thread in esecuzione, né verrà fatto alcun riferimento alla parte o alle parti attive dello stack per quel thread.

+0

_running thread contano come radici? _ O _referenze (all'interno di thread) che fanno riferimento a oggetti contati come radici .._? –

+0

@Royi root - in pratica, la pila dei locali. Nota che arg0 (ovvero questo) di solito mantiene attiva anche l'istanza di destinazione –

+0

Quindi è sbagliato/ok dire: _GC non è autorizzato a raccogliere un thread in esecuzione_? –

2

Il thread non verrà raccolto, poiché ogni thread in esecuzione, in attesa o sospeso viene utilizzato dal GC stesso per decidere cosa è attivo (tracciare tutto nello stack di ogni thread, tracciare tutto ciò che fa riferimento a tutti quegli oggetti, quindi tutto referenziati da quelli, e così via, e hai identificato tutto ciò che non può essere raccolto dalla spazzatura).

Il thread potrebbe terminare, se si trattasse di un thread in background, perché verrà arrestato attivamente quando tutti gli altri thread nel processo saranno terminati. In caso contrario, l'unica cosa che causerà la morte è il processo in corso di uscita, un'eccezione (incluso ThreadAbortException) o l'interruzione del ciclo while stesso.

C'è un caso che è paragonabile per certi versi, che può essere quello che state pensando di:

var timer = new System.Threading.Timer(someCallback, null, new TimeSpan(0, 0, 5), new TimeSpan(0, 0, 5)); 
int someResult = doingSomethingElse(); 
doSomethingElseThatTakesLongerThan5Seconds(); 

Questo è un altro pezzo di codice che causa un altro thread di esecuzione per fare qualcosa. In questo caso, il timer può effettivamente essere garbage collection prima dell'esecuzione, durante una delle esecuzioni, o praticamente in qualsiasi momento dopo il ritorno del costruttore.

La cosa importante è che non c'è un singolo thread per il timer e il thread non "sa" nemmeno dell'oggetto timer. Poiché l'ultimo accesso all'oggetto è accaduto da allora, è idoneo per la raccolta. Questo è diverso dall'argomento di un singolo thread in esecuzione (o in attesa, ecc.).

Problemi correlati