Several java references of understanding

Four references in Java

  • FinalReference strong references
  • SoftReference soft references
  • WeakReference weak references
  • PhantomReference phantom reference

Why provide four references

  • 1, to facilitate jvm garbage collection
  • 2, to facilitate developers, developers have the flexibility to determine the life cycle of certain objects

Four kinds of references to use

FinalReference strong references

After such similar reference Object o = new Object (), to create an object, the reference will be stored in the jvm, and as long as a strong reference exists, the garbage collector will not be recovered modulation referenced

Daily use

Examples of strong references abound, our daily development, we often go to a new object, the new object is out of a strong reference, that is to say as long as the reference exists, the garbage collector will not be recovered out

JVM how to know if a reference exists or not (see another article describes) whether the determination target JVM survival

SoftReference soft references

Soft references are associated, not enough memory in the case, would these soft reference object associated with the inclusion of garbage collection range, and garbage collection, which means that soft references do not completely safe, is not enough memory in the case . will be garbage collected off the demo code:

public class SoftReferenceDemo {
    public static void main(String[] args) {
        int count = 5;
        SoftReference[] softReferences = new SoftReference[count];
        for (int i = 0; i < count; i++) {
            softReferences[i] = new SoftReference<TestObject>(new TestObject("TestObject-" + i));
        }
        //3、打印出softReference中所有的对象
        for (int i = 0; i < count; i++) {
            Object o = softReferences[i].get();
            if (o == null) {
                System.out.println("null");
            } else {
                System.out.println(((TestObject)o).name);
            }
        }
    }
}
复制代码

Examples here a plurality of large objects, then placed softReferences array, named after they traverse the print object in which the print results are as follows:

null
null
null
null
TestObject-4
复制代码

The results can be seen, the first four objects because of insufficient memory is the garbage collected

Daily use:

Soft references are used to indicate that a reference will be collected by GC (garbage disposal) class. When there is a reference point to a time of obj, usually occurs when the GC will not dispose of the object, but the object referenced by soft packaging, when the application memory will be depleted -> OOM imminent, garbage disposal We will take it away. So it seems, the life cycle of software applications is still very long, can be used for caching.

You can create a reference in the following ways:

SoftReference<String> ref = new SoftReference<String>("Hello world");

Receive data:

String value = ref.get();

if (value == null) {
  // 如果被GC回收了 在这里重新初始化
}
// 逻辑处理
...
复制代码

Soft references as a cache:

public class SoftReferenceCache<K,V> {
    private final HashMap<K, SoftReference<V>> mCache;

    public SoftReferenceCache() {
        mCache = new HashMap<K, SoftReference<V>>();
    }

    /**
     * 将对象放进缓存中,这个对象可以在GC发生时被回收
     *
     * @param key key的值.
     * @param value value的值型.
     */

    public void put(K key, V value) {
        mCache.put(key, new SoftReference<V>(value));
    }

    /**
     * 从缓存中获取value
     *
     * @param key
     *
     * @return 如果找到的话返回value,如果被回收或者压根儿没有就返* 回null
     */

    public V get(K key) {
        V value = null;

        SoftReference<V> reference = mCache.get(key);

        if (reference != null) {
            value = reference.get();
        }

        return value;
    }

    /**
     * 从缓存中根据k删除对象
     * @param key
     */
    public void delete(K key){
        mCache.remove(key);
    }
}
复制代码

WeakReference use

Weak references weaker than the soft references before garbage collection occurs under the weak reference object can only be associated to survive, that is to say when GC occurs, regardless of the adequacy of current memory will be recovered out

demo code:

public class WeakReferenceDemo {
    public static void main(String[] args) {
        WeakReference<String> sr = new WeakReference<>(new String("i am here"));
        System.out.println(sr.get());
        //手动gc
        System.gc();
        System.out.println(sr.get());
    }
}
复制代码

First build a weak reference object, and then prints out prior to GC prove that it existed, and then manually call gc, print again, you can see that the object did not have the results are as follows:

i am here
null
复制代码

PhantomReference phantom reference

False quote above and the different places that exist whether an object has a virtual reference, will not constitute how it affects their survival time, and can not be used to obtain an instance of an object through the virtual reference, that is to say with no reference thereto Like association, they are likely to be garbage collected at any time.

Phantom reference role is to receive when the object is recovered collector a notification system, to achieve recovery operation to track the garbage collector, such as when the object is recovered, it will call finalize method of the object.

  • ReferenceQueue reference queue

ReferenceQueue references cited in fact be summarized as a member, and may be a combination of the above three types of reference [soft, weak, references, reference virtual]

When you create a Reference, manually registered to the Reference Queue, whereas when the object is referenced by the Reference garbage collector, JVM will be the Reference on the queue, and we can do other business in this queue , equivalent notification mechanism,

demo code:

public class PhantomReferenceDemo {
    public static void main(String[] args) {
        ReferenceQueue<Object> referenceQueue = new ReferenceQueue<>();
        PhantomReference<Object> phantomReference = new PhantomReference<>(new String("i am here"), referenceQueue);

        //一直返回null,PhantomReference的get()结果必定为null
        System.out.println("phantomReference.get()=" + phantomReference.get());

        System.gc();

        Reference<?> reference;

        while ((reference = referenceQueue.poll()) != null) {
            if (reference == phantomReference) {
                System.out.println("被回收来");
            }
        }
    }
}
复制代码

operation result:

phantomReference.get()=null
被回收了
复制代码

As can be seen from the results get out of the object reference is null, can not be described by an object to obtain a virtual reference example, and after recovery will be queued

Reference related concepts

In order to facilitate the JVM management, Reference is stateful, it can be divided into the following four states:

  • Generally active memory block is assigned a start, and when the change in accessibility of the object referenced gc reference will be placed in a queue and pending pending state status to
  • pending refers ready to be put into the queue of pending objects
  • refers to enqueue memory objects has been recovered to
  • This is the ultimate inactive state, other states can not be changed

Reproduced in: https: //juejin.im/post/5d08b9f9e51d4577770e738c

Guess you like

Origin blog.csdn.net/weixin_33885676/article/details/93166281