值传递 || 引用传递??
值传递(pass by value):是指在调用函数时将实际参数复制一份传递到函数中,这样在函数中如果参数进行修改,将不会影响到实际参数
引用传递(pass by reference):是指在调用函数的时候将实际参数的地址直接传递到函数中,那么在函数中对参数的修改,将影响到实际参数。
区别:值传递会创建副本,引用传递不会
到底是什么传递?
关于 java 中的参数传递是值传递还是引用传递的问题,对于我这个新手来说的确是十分恼火的,之前我的不确定理解(...反正不清楚)是如果传递的参数是普通类型,那就是值传递,如果是对象,那就是引用传递。而在我看到 Hollis 的关于这个问题的讲解时,我豁然开朗,原来 java 中只有值传递呀。
为什么会存在参数是对象类型的时候是引用传递的理解呢?因为有代码证明呀 ~~~(事实是举例不当)
例子 1
public class Test{
public static void main(String[] args){
Test test=new Test();
Elployee elployee=new Employee();
elployee.setName("elployee-A");
elployee.pass(elployee);
System.out.println("print in main,user is "+elployee);
}
public void pass(Employee elployee){
elployee.setName("elployee-B")
System.out.println("print in pass,user is "+elployee);
}
}
输出结果如下:
print in pass,user is {name='elployee-B'}
print in main,user is {name='elployee-B'}
经过 pass 方法后,实参的值竟然被改变了,那么按照上面的引用传递的定义,这不就是引用传递了么,所以有人就得出了在 java 的方法中,传递的是对象类型的时候是引用传递。
但是,这种表述事实上是错误,我们接着看下面一个同样是对象作为参数的情况
例子 2
public class Test{
public static void main(String[] args){
Test test=new Test();
Elployee elployee=new Employee();
elployee.setName("elployee-A");
elployee.pass(elployee);
System.out.println("print in main,user is "+elployee);
}
public void pass(Employee elployee){
elployee=new Employee();
elployee.setName("elployee-B")
System.out.println("print in pass,user is "+elployee);
}
}
输出结果:
print in pass,user is {name='elployee-B'}
print in main,user is {name='elployee-A'}
在上面的 pass 中改变了 elployee 对象,如果是引用传递的话那么在输出应该跟例子 1 一样呀,但是并不一样,这是为什么呢?
事实上在上面的过程中,当我们调用 pass 方法的时候,并把 elployee 作为实际参数传递给形式参数 elployee 的时候,会把实际参数的地址给形式参数,这时形式参数也指向了实际参数的地址。所以在例子 1 中,我们对形式参数的属性进行修改的时候会影响到实际参数,因为此时形式参数持有的地址就是直接参数的地址。而在例子 2 中,形式参数得到实际参数的地址后,我们又对形式参数重新分配一个对象实例,此时形式参数不在只有实际参数的地址,而是持有新建立的对象的地址。
也就是说,这里实际是把实际参数的地址复制了一份,传递给了形式参数。所以这个过程其实是值传递,把实际对象的地址当做了值传递给了形式参数。
更加详细的内容:https://mp.weixin.qq.com/s/F7Niaa7nD1tLApCEGKAj4A
原来是值传递呀!
在了解到 Java 中只有值传递后,脑海中又浮现出好像看到过相关知识的情节。于是再去翻 java 核心技术卷 I 的时候,发现在关于方法参数的那一节讲过这个问题,其中给出了如下例子。
public static void swap(Employee x,Employee y){
Employee temp=x;
x=y;
y=temp;
}
public static void main(String[] args){
Elployee a=new Employee("Alice",...);
Elployee b=new Employee("Bob",...);
swap(a,b);
}
执行 swap(a,b)后,a 仍然是 Alice 而 b 仍然是 Bob。
由此也可以看出参数传递的方式为值传递。
欢迎来到这里!
我们正在构建一个小众社区,大家在这里相互信任,以平等 • 自由 • 奔放的价值观进行分享交流。最终,希望大家能够找到与自己志同道合的伙伴,共同成长。
注册 关于