当前位置:天才代写 > tutorial > JAVA 教程 > 对Java引用的总结

对Java引用的总结

2017-11-02 08:00 星期四 所属: JAVA 教程 浏览:45

副标题#e#

StrongReference、SoftReference、WeakReference、PhantomReferenceJava引用总结–StrongReference、SoftReference、WeakReference、PhantomReference

1 Java引用先容

  Java从1.2版本开始引入了4种引用,这4种引用的级别由高到低依次为:

  强引用  >  软引用  >  弱引用  >  虚引用

⑴强引用(StrongReference)
   强引用是利用最普遍的引用。假如一个工具具有强引用,那垃圾接纳器毫不会接纳它。当内存空间不敷,Java虚拟机甘愿抛出OutOfMemoryError错误,使措施异常终止,也不会靠随意接纳具有强引用的工具来办理内存不敷的问题。

⑵软引用(SoftReference)

   假如一个工具只具有软引用,则内存空间足够,垃圾接纳器就不会接纳它;假如内存空间不敷了,就会接纳这些工具的内存。只要垃圾接纳器没有接纳它,该工具就可以被措施利用。软引用可用来实现内存敏感的高速缓存。

   软引用可以和一个引用行列(ReferenceQueue)连系利用,假如软引用所引用的工具被垃圾接纳器接纳,Java虚拟机就会把这个软引用插手到与之关联的引用行列中。

⑶弱引用(WeakReference)

   弱引用与软引用的区别在于:只具有弱引用的工具拥有更短暂的生命周期。在垃圾接纳器线程扫描它所统领的内存区域的进程中,一旦发明白只具有弱引用的工具,不管当前内存空间足够与否,城市接纳它的内存。不外,由于垃圾接纳器是一个优先级很低的线程,因此不必然会很快发明那些只具有弱引用的工具。

   弱引用可以和一个引用行列(ReferenceQueue)连系利用,假如弱引用所引用的工具被垃圾接纳,Java虚拟机就会把这个弱引用插手到与之关联的引用行列中。

⑷虚引用(PhantomReference)

   “虚引用”顾名思义,就是形同虚设,与其他几种引用都差异,虚引用并不会抉择工具的生命周期。假如一个工具仅持有虚引用,那么它就和没有任何引用一样,在任何时候都大概被垃圾接纳器接纳。

   虚引用主要用来跟踪工具被垃圾接纳器接纳的勾当。虚引用与软引用和弱引用的一个区别在于:虚引用必需和引用行列 (ReferenceQueue)连系利用。当垃圾接纳器筹备接纳一个工具时,假如发明它尚有虚引用,就会在接纳工具的内存之前,把这个虚引用插手到与之 关联的引用行列中。

由于引用和内存接纳干系细密。下面,先通过实例对内存接纳有个认识;然后,进一步通过引用实例加深对引用的相识。

2 内存接纳

建设民众类MyDate,它的浸染是包围finalize()函数:在finalize()中输出打印信息,利便追踪。

说明:finalize()函数是在JVM接纳内存时执行的,但JVM并不担保在接纳内存时必然会挪用finalize()。

MyDate代码如下:

package com.skywang.java;
     
import java.util.Date;
     
public class MyDate extends Date { 
     
    /** Creates a new instance of MyDate */
    public MyDate() {
    }
    // 包围finalize()要领
    protected void finalize() throws Throwable {
        super.finalize();
        System.out.println("obj [Date: " + this.getTime() + "] is gc");
    }   
     
    public String toString() {
        return "Date: " + this.getTime();
    }
}

在这个类中,对java.util.Date类举办了扩展,并重写了finalize()和toString()要领。

建设民众类ReferenceTest,它的浸染是界说一个要领drainMemory():耗损大量内存,以此来激发JVM接纳内存。

ReferenceTest代码如下:

package com.skywang.java;
     
public class ReferenceTest {   
    /** Creates a new instance of ReferenceTest */
    public ReferenceTest() {
    }   
         
    // 耗损大量内存
    public static void drainMemory() {
        String[] array = new String[1024 * 10];
        for(int i = 0; i < 1024 * 10; i++) {
            for(int j = 'a'; j <= 'z'; j++) {
                array[i] += (char)j;
            }           
        }
    }
}

在这个类中界说了一个静态要领drainMemory(),此要领旨在耗损大量的内存,促使JVM运行垃圾接纳。

有了上面两个民众类之后,我们即可测试JVM什么时候举办垃圾接纳。下面分3种环境举办测试:

环境1:排除工具

实现代码:

package com.skywang.java;
     
public class NoGarbageRetrieve {
     
    public static void main(String[] args) {
        MyDate date = new MyDate();
        date = null;
    }
}

运行功效:

<无任何输出>

功效阐明:date固然设为null,但由于JVM没有执行垃圾接纳操纵,MyDate的finalize()要领没有被运行。

环境2:显式挪用垃圾接纳

#p#分页标题#e#

实现代码:

package com.skywang.java;
     
public class ExplicitGarbageRetrieve {
     
    /**
     * @param args
     */
    public static void main(String[] args) {
        // TODO Auto-generated method stub
        MyDate date = new MyDate();
        date = null;
        System.gc();
    }
     
}

运行功效:

obj [Date: 1372137067328] is gc

功效阐明:挪用了System.gc(),使JVM运行垃圾接纳,MyDate的finalize()要领被运行。

环境3:隐式挪用垃圾接纳

实现代码:

package com.skywang.java;
     
public class ImplicitGarbageRetrieve {
     
    /**
     * @param args
     */
    public static void main(String[] args) {
        // TODO Auto-generated method stub
        MyDate date = new MyDate();
        date = null;
        ReferenceTest.drainMemory();
    }
     
}

运行功效:

obj [Date: 1372137171965] is gc

功效阐明:固然没有显式挪用垃圾接纳要领System.gc(),可是由于运行了淹灭大量内存的要领,触发JVM举办垃圾接纳。

总结:JVM的垃圾接纳机制,在内存富裕的环境下,除非你显式挪用System.gc(),不然它不会举办垃圾接纳;在内存不敷的环境下,垃圾接纳将自动运行

3、Java对引用的分类

3.1 强引用

实例代码:

package com.skywang.java;
     
public class StrongReferenceTest {
     
    public static void main(String[] args) {
        MyDate date = new MyDate();
        System.gc();
    }
}

运行功效:


#p#副标题#e#

<无任何输出>

功效说明:纵然显式挪用了垃圾接纳,可是用于date是强引用,date没有被接纳。

3.2 软引用

实例代码:

package com.skywang.java;
     
import java.lang.ref.SoftReference;
     
public class SoftReferenceTest {
     
    public static void main(String[] args) {
        SoftReference ref = new SoftReference(new MyDate());
        ReferenceTest.drainMemory();
    }
}

运行功效:

<无任何输出>

功效说明:在内存不敷时,软引用被终止。软引用被克制时,

SoftReference ref = new SoftReference(new MyDate());
ReferenceTest.drainMemory();

等价于

MyDate date = new MyDate();

// 由JVM抉择运行
If(JVM.内存不敷()) {
date = null;
System.gc();
}

3.3 弱引用

示例代码:

package com.skywang.java;
     
import java.lang.ref.WeakReference;
     
public class WeakReferenceTest {
     
    public static void main(String[] args) {
        WeakReference ref = new WeakReference(new MyDate());
        System.gc(); 
    }
}

运行功效:

obj [Date: 1372142034360] is gc

功效说明:在JVM垃圾接纳运行时,弱引用被终止.

WeakReference ref = new WeakReference(new MyDate());
System.gc();

等同于:

MyDate date = new MyDate();

// 垃圾接纳
If(JVM.内存不敷()) {
date = null;
System.gc();
}

3. 4 假象引用

示例代码:

package com.skywang.java;
     
import java.lang.ref.ReferenceQueue;
import java.lang.ref.PhantomReference;
     
public class PhantomReferenceTest {
     
    public static void main(String[] args) {
        ReferenceQueue queue = new ReferenceQueue();
        PhantomReference ref = new PhantomReference(new MyDate(), queue);
        System.gc();
    }
}

运行功效:

obj [Date: 1372142282558] is gc

功效说明:假象引用,在实例化后,就被终止了。

ReferenceQueue queue = new ReferenceQueue();
PhantomReference ref = new PhantomReference(new MyDate(), queue);
System.gc();

等同于:

MyDate date = new MyDate();
date = null;

可以用以下表格总结上面的内容:

#p#副标题#e#

对Java引用的总结

点击下载:源代码

 

    关键字:


天才代写-代写联系方式