Ho cercato un sacco di riferimenti phantom ma non ho trovato il suo utilizzo pratico. E logicamente il metodo get() restituisce null in caso di riferimenti PhantomQual è l'uso pratico dei riferimenti fantasma - JAVA?
risposta
Puoi seguire questa blog:
cosa servono PhantomReferences? Sono a conoscenza solo di due casi gravi per loro: in primo luogo, consentono di determinare esattamente quando un oggetto è stato rimosso dalla memoria. Sono infatti l'unico modo per determinare quello . Questo non è generalmente utile, ma potrebbe essere utile in alcune circostanze molto specifiche come la manipolazione di immagini di grandi dimensioni: se si sa per certo che un'immagine deve essere raccolta dei dati inutili, è possibile attendere fino a quando non è effettivamente prima di tentare di caricare l'immagine successiva, e quindi rende meno probabile il temuto OutOfMemoryError.
In secondo luogo, PhantomReferences evitare un problema fondamentale con finalizzazione: finalizzare() metodi possono "resuscitare" gli oggetti con la creazione di nuovi forti riferimenti ad essi. Quindi cosa dici? Bene, il problema è che un oggetto che sovrascrive finalize() deve ora essere determinato per essere immondizia in almeno due cicli di garbage collection separati al fine di raccogliere . Quando il primo ciclo determina che è spazzatura, diventa disponibile per la finalizzazione . A causa della (sottile, ma purtroppo reale) possibilità che l'oggetto fosse "resuscitato" durante la finalizzazione, il garbage collector deve essere eseguito nuovamente prima che l'oggetto possa essere effettivamente rimosso. E poiché la finalizzazione potrebbe non essere stata eseguita in modo tempestivo, , un numero arbitrario di cicli di raccolta di immondizia potrebbe essersi verificato mentre l'oggetto era in attesa della finalizzazione . Questo può significare seri ritardi nella pulizia degli oggetti inutili di ed è il motivo per cui è possibile ottenere OutOfMemoryErrors anche quando la maggior parte dell'heap è spazzatura.
Leggi anche: The Mysterious Phantom Reference
Si consideri il seguente codice.
public class Foo { private String bar; public Foo(String bar) { this.bar = bar; } public String foo() { return bar; } }
Allora supponiamo dopo che l'oggetto è stato completamente dereferenziati dal applicazione che voglio in qualche modo chiamare foo(). Ecco un codice che I si aspettava che funzionasse con una sola pecca.
// initialize ReferenceQueue<Foo> queue = new ReferenceQueue<Foo>(); ArrayList< PhantomReference<Foo>> list=new ArrayList<PhantomReference<Foo>>(); for (int i = 0; i < 10; i++) { Foo o = new Foo(Integer.toOctalString(i)); list.add(new PhantomReference<Foo>(o, queue)); } // make sure the garbage collector does it’s magic System.gc(); // lets see what we’ve got Reference<? extends Foo> referenceFromQueue; for (PhantomReference<Foo> reference : list) System.out.println(reference.isEnqueued()); while ((referenceFromQueue = queue.poll()) != null) { System.out.println(referenceFromQueue.get()); referenceFromQueue.clear(); }
PhantomReference prende un'istanza di Foo e un ReferenceQueue. Dal nessuna maniglia viene mantenuta su Foo, dovrebbe essere immediatamente morta. Quindi, dire alla la VM da raccogliere perché non c'è abbastanza heap per attivare una collezione in modo naturale. La prima cosa che chiederò al PhantomReference è; sei stato agganciato? In questo caso la risposta sarà vera. Successivamente chiedo la coda per il riferimento ma, come potete vedere, la chiamata get() restituisce sempre null. Informazioni sull'unica soluzione che aveva il valore era racchiudere le risorse o gli oggetti che si desideravano interagire con in una sottoclasse di PhantomReference.
public class FinalizeStuff<Foo> extends PhantomReference<Foo> { public FinalizeStuff(Foo foo, ReferenceQueue<? super Foo> queue) { super(foo, queue); } public void bar() { System.out.println("foobar is finalizing resources"); } }
In questo caso non ho intenzione di avvolgere Foo nella sottoclasse come che sembrano violare lo spirito di PhantomReference. Invece vado a avvolgere le risorse associate a Foo e interagire con loro. Ora posso fare questo.
// initialize ReferenceQueue<Foo> queue = new ReferenceQueue<Foo>(); ArrayList< FinalizeStuff<Foo>> list = new ArrayList<FinalizeStuff<Foo>>(); ArrayList<Foo> foobar = new ArrayList<Foo>(); for (int i = 0; i < 10; i++) { Foo o = new Foo(Integer.toOctalString(i)); foobar.add(o); list.add(new FinalizeStuff<Foo>(o, queue)); } // release all references to Foo and make sure the garbage collector does it’s magic foobar = null; System.gc(); // should be enqueued Reference<? extends Foo> referenceFromQueue; for (PhantomReference<Foo> reference : list) { System.out.println(reference.isEnqueued()); } // now we can call bar to do what ever it is we need done while ((referenceFromQueue = queue.poll()) != null) { ((FinalizeStuff)referenceFromQueue).bar(); referenceFromQueue.clear(); }
- 1. Quando utilizzare i riferimenti fantasma in Java?
- 2. Qual è l'uso pratico dell'eredità protetta?
- 3. Qual è l'effetto pratico di viewPager.setOffscreenPageLimit (3) ;?
- 4. Qual è il costo dei riferimenti di assemblaggio non utilizzati?
- 5. Perché l'inizializzazione dei riferimenti a null è consentita in Java?
- 6. copia dei riferimenti una mappa in Java
- 7. Qual è l'uso pratico di MPS IDEA e Eclipse xtext
- 8. Confronto dei riferimenti oggetto JNI
- 9. Uso pratico dei futures? Cioè, come ucciderli?
- 10. È possibile ottenere il conteggio dei riferimenti agli oggetti?
- 11. Ottenere la gerarchia dei riferimenti di caricamento della classe Java
- 12. uso pratico di IdentityHashMap in Java 6
- 13. Java statici auto-riferimenti
- 14. Qual è l'ordine dei costruttori in questo codice Java?
- 15. Qual è il significato dei valori da Java Process.exitValue()?
- 16. Qual è l'equivalente dei caratteri jolly Java nei generici C#
- 17. Riferimenti simbolici in Java
- 18. Definizione dei tipi di fantasma - impossibile compilare esempi
- 19. Chiarimento dei riferimenti in C++
- 20. Toolkit GUI pratico?
- 21. Qual è l'uso pratico della pigrizia come caratteristica del linguaggio incorporato?
- 22. Java: Stack con riferimenti deboli
- 23. Qual è il modo più pratico per elencare tutti i pacchetti installati in Sublime Text 3?
- 24. Uso pratico di `foldl`
- 25. Qual è l'operatore & = per Java
- 26. Qual è l'equivalente Smalltalk di Java statico?
- 27. Java: è possibile avere riferimenti di classe finale reciproci?
- 28. Qual è lo scopo del pool di costanti Java?
- 29. utilizzo corretto dei riferimenti rvalue come parametri
- 30. Android - memorizzazione dei riferimenti a ApplicationContext