¿Alguien puede explicar la diferencia entre las tres clases de referencia (o publicar un enlace a una buena explicación)? SoftReference> WeakReference> PhantomReference, Pero cuando iba a utilizar cada uno? ¿Por qué hay un WeakHashMappero no SoftHashMapo PhantomHashMap?
Y si uso el siguiente código ...
WeakReference<String> ref = new WeakReference<String>("Hello!");
if (ref != null) { // ref can get collected at any time...
System.gc(); // Let's assume ref gets collected here.
System.out.println(ref.get()); // Now what?!
}
...¿lo que pasa? ¿Tengo que verificar si refes nulo antes de cada declaración (esto está mal, pero qué debo hacer)? Perdón por las preguntas rápidas, pero tengo problemas para entender estas Referenceclases ... ¡Gracias!
java
reference
weak-references
phantom-reference
soft-references
Haywood Jablomey
fuente
fuente

WeakHashMappero noSoftHashMapoPhantomHashMapExcelente, por qué no me di cuenta de esto antes ... ??ref != nullcheque no tiene sentido.refnunca lo seránull.strongRef --> weakRef --> objA. Ahora, seráobjAGCed o no, ya que tiene una referencia indirecta destrongRef.Respuestas:
La documentación de la
java.lang.refbiblioteca de Java para el paquete caracteriza la fuerza decreciente de los tres tipos de referencia explícitos.Utiliza un
SoftReferencecuando desea que el objeto referenciado permanezca activo hasta que el proceso del host se esté quedando sin memoria. El objeto no será elegible para la recopilación hasta que el recopilador necesite liberar memoria. Enunciado libremente, vincular unSoftReferencemedio, "Fija el objeto hasta que no puedas más".Por el contrario, utilice a
WeakReferencecuando no desee influir en la vida útil del objeto al que se hace referencia; simplemente desea hacer una afirmación separada sobre el objeto al que se hace referencia, siempre que permanezca vivo. La elegibilidad del objeto para la colección no está influenciada por la presencia de enlacesWeakReference. Algo así como un mapeo externo de la instancia del objeto a la propiedad relacionada, donde la propiedad solo necesita registrarse mientras el objeto relacionado esté vivo, es un buen uso paraWeakReferences yWeakHashMap.El último ...
PhantomReferencees más difícil de caracterizar. PorWeakReferenceejemplo, tal límitePhantomReferenceno ejerce ninguna influencia en la vida útil del objeto referenciado. Pero a diferencia de los otros tipos de referencia, ni siquiera se puede eliminar la referencia aPhantomReference. En cierto sentido, no apunta a lo que apunta, por lo que las personas que llaman pueden saber. Simplemente le permite a uno asociar algunos datos relacionados con el objeto referenciado, datos que luego se pueden inspeccionar y actuar sobre ellos cuandoPhantomReferencese pone en cola en su relacionadoReferenceQueue. Normalmente, se deriva un tipoPhantomReferencee incluye algunos datos adicionales en ese tipo derivado. Desafortunadamente, hay algo de abatimiento involucrado para hacer uso de un tipo derivado.En su código de ejemplo, no es la
refreferencia (o, si lo prefiere, la "variable") la que puede ser nula. Más bien, es el valor obtenido al llamarReference#get()que puede ser nulo. Si se determina que es nulo, es demasiado tarde; el objeto referenciado ya está en camino de ser recopilado:final String val = ref.get(); if (null != val) { // "val" is now pinned strongly. } else { // "val" is already ready to be collected. }fuente
strongRef --> weakRef --> objA. Ahora, seráobjAGCed o no, ya que tiene una referencia indirecta destrongRef.objAes elegible para la recolección como basura. Fijar unWeakReferenceno ejerce ninguna influencia sobre el objeto al queWeakReferenceapunta.objAque se recolecte basura, la referencia débil debe eliminarse primero a la derecha. Y una fuerte referencia está apuntando a los débiles referencia por el que los débiles no elegible para ser ref GCedWeakReferenceno es necesario recolectarlo para permitirobjAsu recolección. ElWeakReferenceno se mantieneobjAvivo. Más bien, es una forma de encontrarobjAmientras está vivo, sin influir en esa vida, y detectar cuándo el coleccionista ya se lo llevó.Un enlace: https://community.oracle.com/blogs/enicholas/2006/05/04/understanding-weak-references
PhantomHashMapNo funcionaría muy bien, ya quegetsiempre devuelvenullpara referencias fantasmas.Los cachés son difíciles, por lo
SoftHashMapque es posible que no funcionen tan bien como crees. Sin embargo, creo que la biblioteca de colecciones de Google contiene una implementación de mapa de referencia general.Siempre debe verificar que
getdevuelve no-null. (Tenga en cuenta que no comprobar que laReferencereferencia en sí no sea-null.) En el caso de cadenas internas, siempre lo hará, pero (como siempre) no intente ser "inteligente" al respecto.fuente
strongRef --> weakRef --> objA. Ahora, seráobjAGCed o no, ya que tiene una referencia indirecta destrongRef.También debe mencionarse, como se indica en el comentario de Truong Xuan Tinh, aquí: http://blog.yohanliyanage.com/2010/10/ktjs-3-soft-weak-phantom-references/
Que JRockit JVM implementa referencias débiles / suaves / fantasmas de manera diferente a Sun JVM.
fuente
String str = new String("hello, world"); WeakReference<String> ref = new WeakReference<String>(str); str = null; if (ref != null) { System.gc(); System.out.println(ref.get()); }En este caso, generará un valor nulo. La llamada a
System.gc()es importante aquí.fuente