Domanda

Se chiamo finalize() su un oggetto dal mio codice di programma, il file JVM esegui ancora di nuovo il metodo quando il Garbage Collector elabora questo oggetto?

Questo sarebbe un esempio approssimativo:

MyObject m = new MyObject();

m.finalize();

m = null;

System.gc()

Sarebbe la chiamata esplicita a finalize() fare il JVMdi Garbage Collector di non eseguire il file finalize() metodo sull'oggetto m?

È stato utile?

Soluzione

Secondo questo semplice programma di test, la JVM effettuerà comunque la chiamata a finalize() anche se l'hai chiamata esplicitamente:

private static class Blah
{
  public void finalize() { System.out.println("finalizing!"); }
}

private static void f() throws Throwable
{
   Blah blah = new Blah();
   blah.finalize();
}

public static void main(String[] args) throws Throwable
{
    System.out.println("start");
    f();
    System.gc();
    System.out.println("done");
}

L'output è:

inizio
finalizzazione!
finalizzazione!
Fatto

Ogni risorsa là fuori dice di non chiamare mai finalize() esplicitamente, e praticamente non implementare mai il metodo perché non ci sono garanzie su se e quando verrà chiamato.Faresti meglio a chiudere manualmente tutte le tue risorse.

Altri suggerimenti

È necessario comprendere il flusso di lavoro del Garbage Collector (GC) per comprendere la funzione di finalizzazione.la chiamata a .finalize() non invocherà il garbage collector, né la chiamata a system.gc.In realtà, ciò che finalize aiuterà il programmatore è dichiarare il riferimento dell'oggetto come "senza riferimento".

GC impone una sospensione dell'esecuzione di JVM, il che crea un'ammaccatura sulle prestazioni.Durante il funzionamento, GC attraverserà tutti gli oggetti a cui si fa riferimento, a partire dall'oggetto radice (la chiamata al metodo principale).Questo tempo di sospensione può essere ridotto dichiarando manualmente gli oggetti come senza riferimenti, poiché ridurrà i costi operativi per dichiarare obsoleto il riferimento all'oggetto da parte dell'esecuzione automatizzata.Dichiarando finalize(), il codificatore imposta il riferimento all'oggetto obsoleto, quindi alla successiva esecuzione dell'operazione GC, l'esecuzione GC spazzerà gli oggetti senza utilizzare il tempo dell'operazione.

Citazione:"Dopo che il metodo finalize è stato invocato per un oggetto, non viene intrapresa alcuna ulteriore azione finché la Java virtual machine non ha nuovamente determinato che non esiste più alcun mezzo con cui è possibile accedere a questo oggetto da parte di qualsiasi thread che non sia ancora morto, inclusi eventuali azioni di altri oggetti o classi pronte per essere finalizzate, a quel punto l'oggetto può essere scartato." dal documento API Java su java.Object.finalize();

Per una spiegazione dettagliata, puoi anche controllare: javabook.computerware

Il metodo finalize non viene mai richiamato più di una volta da una JVM per un dato oggetto.Non dovresti comunque fare affidamento su finalize perché non c'è garanzia che venga richiamato.Se stai chiamando finalize perché devi eseguire il codice di pulizia, è meglio inserirlo in un metodo separato e renderlo esplicito, ad esempio:

public void cleanUp() {
  .
  .
  .
}

myInstance.cleanUp();
Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top