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

简介: 作为Java世界的核心内容,类与对象凭借其引用数据类型的内在特质,实现了引用传递的能力,为整个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的课程吗?从小白到大神,从入门到精通,更多精彩不容错过!免费为您提供更多的学习资源。
本内容视频来源于阿里云大学

下一篇:保守VS开放?搞懂封装对象属性 | 带你学《Java面向对象编程》之四
更多Java面向对象编程文章查看此处

相关文章
|
1天前
|
Java
04|零基础玩转面向对象编程:Java OOP
04|零基础玩转面向对象编程:Java OOP
5 0
|
1天前
|
Java
【JAVA基础篇教学】第五篇:Java面向对象编程:类、对象、继承、多态
【JAVA基础篇教学】第五篇:Java面向对象编程:类、对象、继承、多态
|
2天前
|
缓存 Java 程序员
关于创建、销毁对象⭐Java程序员需要掌握的8个编程好习惯
关于创建、销毁对象⭐Java程序员需要掌握的8个编程好习惯
关于创建、销毁对象⭐Java程序员需要掌握的8个编程好习惯
|
2天前
|
Java
从源码出发:JAVA中对象的比较
从源码出发:JAVA中对象的比较
9 3
|
2天前
|
安全 Java 编译器
java中类与对象回顾总结-2
java中类与对象回顾总结
14 3
|
2天前
|
Java 编译器
java中类与对象回顾总结-1
java中类与对象回顾总结
14 3
|
3天前
|
存储 Java 程序员
Java面向对象编程的基础概念解析
Java面向对象编程的基础概念解析
13 0
|
3天前
|
Java
Java一分钟之-类与对象:面向对象编程入门
【5月更文挑战第8天】本文为Java面向对象编程的入门指南,介绍了类与对象的基础概念、常见问题及规避策略。文章通过代码示例展示了如何定义类,包括访问修饰符的适当使用、构造器的设计以及方法的封装。同时,讨论了对象创建与使用时可能遇到的内存泄漏、空指针异常和数据不一致等问题,并提供了相应的解决建议。学习OOP需注重理论与实践相结合,不断编写和优化代码。
26 1
|
9天前
|
SQL Java 数据库连接
15:MyBatis对象关系与映射结构-Java Spring
15:MyBatis对象关系与映射结构-Java Spring
29 4
|
12天前
|
Java 编译器
【Java探索之旅】解密构造方法 对象初始化的关键一步
【Java探索之旅】解密构造方法 对象初始化的关键一步
16 1