開發與維運

对象“变形记”——初识引用与GC | 带你学《Java面向对象编程》之三

上一篇:带你“找对象”--Java内存分析 | 带你学《Java面向对象编程》之二
【本节目标】
通过阅读本章,你将通过多组实例从内存上深度了解通过对象声明、方法调用等方法进行引用传递的原理,并深刻理解引用为何会产生内存垃圾以及GC机制的相关内容。

3.1 引用传递分析

类本身属于引用数据类型,既然是引用数据类型,那么就牵扯到内存的引用传递,所谓的引用传递的本质:同一块堆内存的空间可以被不同的栈内存所指向,也可以更换指向。
范例:定义一个引用传递的分析程序

public class JavaDemo {
    public static void main(String args[]) {
      Person per1 = new Person() ;     //声明并实例化对象
      per1.name = “张三” ;
      per1.age = 18 ;
      Person per2 = per1 ; //引用传递
      per2.age =80 ;
      per1.tell() ;            //进行方法的调用
   }
}

image.png
图一 运行结果一

image.png
图二 内存分析结果一

这个时候的引用传递是直接在主方法之中定义的,也可以通过方法实现引用传递
范例:利用方法实现引用传递处理

public class JavaDemo {
    public static void main(String args[]) {
      Person per = new Person() ;     //声明并实例化对象
      per.name = “张三” ;
      per.age = 18 ;
      change(per) ;     //等价于:Person temp = per ;
      per.tell() ;            //进行方法的调用
}
public static void change(Person  temp){
    temp.age = 80 ;
   }
}

image.png
图三 运行结果二

image.png
图四 内存分析结果二

与之前的差别最大的地方在于,此时的程序是将Person类的实例化对象(内存地址、数值)传递到了change方法之中,由于传递的是一个Person类型,那么change()方法接收的也是Person类型。
引用传递可以发生在方法上,这个时候一定要观察方法的参数类型,同时也要观察方法的执行过程。

3.2 引用与垃圾产生分析

经过一系列分析后,所有的引用传递的本质就是一场堆内存的调戏游戏。但是对于引用传递,如果处理不当,那么也会造成垃圾的产生,那么本次将针对于垃圾产生的原因进行简单分析。
范例:定义一个要分析的程序

public class JavaDemo {
    public static void main(String args[]) {
      Person per1 = new Person() ;     //声明并实例化对象
      Person per2 = new Person() ;
      per1.name = “张三” ;
      per1.age = 18 ;
      per2.name = “李四” ; 
      per2.age =19 ;
      per2 = per1 ;         //引用传递
      per2.age =80 ;
      per1.tell() ;            //进行方法的调用
   }
}

image.png
图五 运行结果三

此时已经明确发生了引用传递,并且也成功的完成了引用传递的处理操作,但是下面来观察一下其内存的分配与处理操作。
一个栈内存只能够保存有一个一堆内存的地址数据,如果发生更改,则之前的地址数据将从此栈内存中彻底消失。下面来看看它的内存分析结果。

image.png
图六 内存分析结果三

所谓的垃圾空间指的就是没有任何栈内存所指向的堆内存空间,所有的垃圾将被GC(Garbage Collector、垃圾收集器)不定期进行回收并且释放无用内存空间,但是如果垃圾过多,一定将影响到GC的处理性能,从而降低整体的程序性能。那么在实际开发之中,对于垃圾的产生应该越少越好。
想学习更多的Java的课程吗?从小白到大神,从入门到精通,更多精彩不容错过!免费为您提供更多的学习资源。
本内容视频来源于阿里云大学
更多Java面向对象编程文章查看此处


Leave a Reply

Your email address will not be published. Required fields are marked *