JAVA:形参改变对实参的影响
熟悉C/C++的同学都知道,如果想在传入形参的函数中,实现形参改变,实参也跟着改变的话,我们需要手动将实参的地址或引用传入给形参,这样形参生成的拷贝副本,就是实参指向存储单元的地址,也就是说,形参的改变会导致实参也跟着改变。
但是由于Java的JVM的机制,我们并不能够获得真正的存储地址,是JVM根据不同的平台自动分配,这也就导致了我们不能手动传递地址,JAVA将自动为引用传递传递一个地址。
一、两种类型:基本类型 和 引用类型
基本类型的变量保存原始值,即它代表的值就是数值本身, 原始值一般对应在内存上的栈区;基本类型包括: byte
, short
, int
, long
, char
, float
, double
, boolean
这八大基本数据类型
引用类型的变量保存引用值,引用值指向内存空间的地址。代表了某个对象的引用,而不是对象本身。对象本身存放在这个引用值所表示的地址的位置。被引用的对象对应内存上的堆内存区。引用类型包括: 类类型
, 接口类型
和 数组
。
基本类型和引用类型的区别:基本数据类型在声明时系统就给它分配空间;而引用数据类型不同,它声明时只给变量分配了引用空间,而不分配数据空间。
二、值传递和引用传递
值传递:方法调用时,实际参数把它的值传递给对应的形式参数,函数接收的是原始值的一个拷贝, 此时内存中存在两个相等的基本类型,即实际参数和形式参数,后面方法中的操作都是对形参这个值的修改,不影响实际参数的值。
引用传递:也称为地址传递、址传递。方法调用时,实际参数的引用(地址,而不是参数的值)被传递给方法中相对应的形式参数,函数接收的是原始值的内存地址在方法执行中,形参和实参内容相同,指向同一块内存地址,方法执行中对引用的操作将会影响到实际对象。
通常 基本类型 和 String 传递是值传递,形参的改变不会影响实参的改变
补充:为什么String的传递不会改变实参的值?
String表现为值传递,主要是因为这个玩意儿是不可变的!如何理解不可变?我们一般说的改变一个String变量,其实并不是改变的这个String本身,而是用一个新的String去替换掉原来的,原来的String本身并没有变。
这点类似于C++,在我们不传递地址或引用时,C++会创建一个新的实例,而新实例的改变并不会影响原来实参的数据。类似的,由于String的不可变性,导致在改变值的时候会创造一个新的实例,形参会指向新的实例而不是改变它本身,这就导致了和值传递一样的效果。
参考:
[1] https://blog.csdn.net/qq_36761831/article/details/82817803
[2] https://www.zhihu.com/question/47306147