java cos'è collector - L'utilizzo di final per le variabili in Java migliora la garbage collection?




7 Answers

Ecco un esempio leggermente diverso, uno con i campi del tipo di riferimento finale piuttosto che le variabili locali del tipo valore finale:

public class MyClass {

   public final MyOtherObject obj;

}

Ogni volta che crei un'istanza di MyClass, creerai un riferimento in uscita a un'istanza MyOtherObject e il GC dovrà seguire quel collegamento per cercare oggetti live.

La JVM utilizza un algoritmo GC di mark-sweep, che deve esaminare tutti i riferimenti live nelle posizioni "root" del GC (come tutti gli oggetti nello stack di chiamate corrente). Ogni oggetto live è "contrassegnato" come "vivo" e qualsiasi oggetto a cui fa riferimento un oggetto live viene anche contrassegnato come "vivo".

Dopo il completamento della fase mark, il GC trascina l'heap, liberando memoria per tutti gli oggetti non marcati (e compattando la memoria per gli oggetti live rimanenti).

Inoltre, è importante riconoscere che la memoria heap di Java è suddivisa in una "giovane generazione" e una "vecchia generazione". Tutti gli oggetti sono inizialmente assegnati nella giovane generazione (a volte indicato come "l'asilo nido"). Poiché la maggior parte degli oggetti ha vita breve, il GC è più aggressivo nel liberare la spazzatura recente dalla giovane generazione. Se un oggetto sopravvive a un ciclo di raccolta della giovane generazione, viene spostato nella vecchia generazione (a volte indicata come "generazione di ruolo"), che viene elaborata meno frequentemente.

Quindi, in cima alla mia testa, ho intenzione di dire "no, la modifica" finale "non aiuta il GC a ridurre il carico di lavoro".

Secondo me, la migliore strategia per ottimizzare la gestione della memoria in Java è eliminare i riferimenti spuri il più rapidamente possibile. Puoi farlo assegnando "null" a un riferimento a un oggetto non appena hai finito di usarlo.

O, meglio ancora, minimizzare la dimensione di ogni ambito di dichiarazione. Ad esempio, se dichiari un oggetto all'inizio di un metodo a 1000 righe e se l'oggetto rimane attivo fino alla chiusura dell'ambito del metodo (l'ultima parentesi graffa chiusa), l'oggetto potrebbe rimanere in vita per molto più tempo che effettivamente necessario.

Se si utilizzano metodi piccoli, con solo una dozzina di righe di codice, gli oggetti dichiarati all'interno di tale metodo cadranno fuori dall'ambito più rapidamente e il GC sarà in grado di svolgere gran parte del proprio lavoro all'interno del più efficiente giovane generazione. Non vuoi che gli oggetti vengano spostati nella vecchia generazione a meno che non sia assolutamente necessario.

example c++

Oggi i miei colleghi e io abbiamo una discussione sull'uso della parola chiave final in Java per migliorare la garbage collection.

Ad esempio, se scrivi un metodo come:

public Double doCalc(final Double value)
{
   final Double maxWeight = 1000.0;
   final Double totalWeight = maxWeight * value;
   return totalWeight;  
}

Dichiarare le variabili nel metodo final aiuterebbe la garbage collection a ripulire la memoria dalle variabili inutilizzate nel metodo dopo l'uscita del metodo.

È vero?




No, enfaticamente non è vero.

Ricorda che il final non significa costante, significa solo che non puoi cambiare il riferimento.

final MyObject o = new MyObject();
o.setValue("foo"); // Works just fine
o = new MyObject(); // Doesn't work.

Potrebbero esserci alcune piccole ottimizzazioni basate sulla consapevolezza che la JVM non dovrà mai modificare il riferimento (come non avere il controllo per vedere se è cambiato), ma sarebbe così lieve da non preoccuparsi.

Final dovrebbe essere pensata come utile meta-dati per lo sviluppatore e non come ottimizzazione del compilatore.




Bene, non so sull'uso del modificatore "finale" in questo caso, o del suo effetto sul GC.

Ma posso dirti questo: il tuo uso di valori in Box piuttosto che di primitive (ad es. Double invece di double) allocherà quegli oggetti sull'heap piuttosto che sullo stack, e produrrà inutili spazzatura che il GC dovrà ripulire.

Io uso solo primitive in scatola quando richiesto da un'API esistente o quando ho bisogno di primati nullable.




GC agisce su referenze irraggiungibili. Questo non ha nulla a che vedere con "finale", che è semplicemente un'affermazione di un incarico una tantum. È possibile che alcuni GC di VM possano utilizzare "finale"? Non vedo come o perché.




final su variabili e parametri locali non fa differenza per i file di classe prodotti, quindi non può influenzare le prestazioni di runtime. Se una classe non ha sottoclassi, HotSpot tratta tale classe come se fosse definitiva in ogni caso (può annullare successivamente se una classe che interrompe quell'assunzione viene caricata). Credo che i metodi final siano più o meno gli stessi delle classi. final su campo statico può consentire alla variabile di essere interpretata come una "costante in fase di compilazione" e l'ottimizzazione deve essere eseguita da javac su tale base. final sui campi consente alla JVM una certa libertà di ignorare le relazioni di avvenimenti prima .




Tutti i metodi e le variabili possono essere sovrascritti da default nelle sottoclassi. Se vogliamo salvare le sottoclassi da overridig dei membri della superclasse, possiamo dichiararle come finali usando la parola chiave final. Per eg- final int a=10; final void display(){......} Il completamento di un metodo garantisce che le funzionalità definite nella superclasse non vengano mai modificate. Allo stesso modo il valore di una variabile finale non può mai essere cambiato. Le variabili finali si comportano come variabili di classe.




assolutamente, a patto che la vita dell'oggetto sia più breve e produca grandi benefici nella gestione della memoria, recentemente abbiamo esaminato la funzionalità di esportazione con variabili di istanza su un test e un altro test con variabile locale a livello di metodo. durante il test di carico, JVM getta outofmemoryerror al primo test e JVM viene fermato. ma in un secondo test, è riuscito a ottenere il report correttamente grazie a una migliore gestione della memoria.




Related