1.1 理解
- 在默认情况下,通过 System.gc()或者 Runtime. getruntime().gc()的调用,会显式触发Full GC,同时对老年代和新生代进行回收,甚至会包含方法区的回收,尝试释放被丢弃对象占用的内存 。
- 然而 System.gc()调用附带一个免责声明,无法保证对垃圾收集器的调用
- JVM实现者可以通过 System.gc()调用来决定JVM的GC行为。而一般情况下,垃圾回收应该是自动进行的,无须手动触发,否则就太过于麻烦了。在一些特殊情况下,如我们正在编写一个性能基准,我们可以在运行之间调用System.gc()
1.2 代码例子
localvarGC1方法在进行Young GC的时候没有被回收掉,在进行Full GC的时候就直接将buffer对象放入了老年代。
localvarGC2方法里的对象在经过young GC和Full GC后,整个对象已经被回收掉了。
localvarGC2方法中在进行Young GC的时候没有被回收掉,在进行Full GC的时候就直接将buffer对象放入了老年代。
之所以没有被回收掉是因为在自己码中最大的索引位置为2,虽然在局部变量表中只有一个位置,但buffer是占用了一个索引位置,buffer还是指引着堆中的对象,所以没有被回收掉。
localvarGC4方法里的对象在经过young GC和Full GC后,整个对象已经被回收掉了。
之所以能被回收掉是因为本来buffer在局部变量表中占据一个槽位,但它的作用域只是在静态代码块中,在静待代码块后有定义了一个value的变量,此变量就会覆盖buffer所占据的槽位,没有引用在指向堆中的byte对象,所以就可以被回收掉了。
localvarGC1经历4次GC后最终被回收掉了。