Java 传递参数是值传递还是引用传递?
Java是值传递!Java是值传递!Java是值传递!
无论是基本类型具体值还是引用类型的引用地址值都是值传递。
看下面这个例子
package com.yang.passbyvalue;
import java.util.Arrays;
/**
* 基本数据类型传的是克隆的一个值,
* 引用类型传的是克隆指向对象地址值的一个值
*/
public class Demo {
public static void change(int a) {
a = 2;
System.out.println("我是方法里的a:" + a);
}
public static void changArray(int[] data) {
data[0] = 3;
data[1] = 4;
System.out.println("我是方法里的data:" + Arrays.toString(data));
}
}
class Test {
public static void main(String[] args) {
//初始化基本数据类型
int a = 0;
System.out.println("我是初始化的a:" + a);
Demo.change(a);
System.out.println("我是change后的a:" + a);
//初始化引用数据类型
int[] data = {1, 2};
System.out.println("我是初始化的data:" + Arrays.toString(data));
Demo.changArray(data);
System.out.println("我是change后的data:" + Arrays.toString(data));
}
}
我是初始化的a:0
我是方法里的a:2
我是change后的a:0
我是初始化的data:[1, 2]
我是方法里的data:[3, 4]
我是change后的data:[3, 4]
结果,基础类型值没有改变,引用类型值随方法改变而改变了
基础数据类型传递的是一份数据拷贝,所以在change()
里修改了方法里的a
的值并不会影响初始值,而对于数组(引用类型),changArray()
修改了地址引用指向的对象的值,所以原来引用指向该对象的值都随之改变了。
再来看看下面这个例子
package com.yang.passbyvalue;
public class StringDemo {
public static void change(String s) {
s = "aaa";
System.out.println("我是方法里的s:" + s);
}
}
class StringDemoTest {
public static void main(String[] args) {
String s = "a";
System.out.println("我是初始化的s:" + s);
StringDemo.change(s);
System.out.println("我是修改后的s:" + s);
}
}
我是初始化的s:a
我是方法里的s:aaa
我是修改后的s:a
String
类型作为引用数据类型,为什么在方法里修改了,但是没有影响原先的值?
String
底层是被final
修饰的 char[]
,值是不能被修改的
字面值 "a"
初始化的时候,会先将 "a"
放进字符串常量池中, s
保存的是引用地址值,当调用change()
方法时,将地址值传过去,s = "aaa";
会先去常量池中找 "aaa"
,找到返回 "aaa"
的地址引用,找不到创建一个"aaa"
,返回新建的"aaa"
的地址引用,新的引用覆盖传过来的引用 s
,但是初始化的 s
任然保存的是指向 "a"
的地址引用。这恰恰说明了 Java 里是值传递。