按值传递: 传递的是值的传递,传递之后互不相关
public class Test2 {
private void test1(int a){
a =5;
System.out.println("test1方法中a="+a);
}
public static void main(String[] args) {
Test2 t = new Test2();
int a = 3;
t.test1(a);
System.out.println("main方法中a="+a);
}
}
运行结果:
test1方法中a=5
main 方法中 a = 3
按引用传递:
指的是在方法调用时,传递的参数是按照引用进行传递,其实传递的引用的地址,就是变量所对应的内存空间的地址。
class Instance{
public int num = 0 ;
}
public class Test2 {
public void dothis(Instance p1){
p1.num = 20;//4
System.out.println("dothis中num的值是"+p1.num);
}
public static void main(String[] args) {
Instance p = new Instance();//1
p.num = 10;//2
Test2 t = new Test2();
t.dothis(p);//3
System.out.println("main中num的值是"+p.num);
}
}
运行结果:
dothis中num的值是20
main中num的值是20
理解按引用传递 过程中的内存分配,根据上面的例子来说
1. 第一步:创建instance实例对象,并有引用 p -> instance 实例(此时num=0),p存储实例变量的地址
2. 第二步: 修改instance实例对象中num的值,此时有 p - > instance实例(num=10)
3. 第三步:将引用p,作为参数调用dothis方法,注意 引用 p 和方法参数p1,不是同一个变量,但是存储的
instance实例的地址是相同的,就是两变量都是指向同一个实例对象: p->instance实例(num=10), p1->instance实例(num=10)
4. 第四步:dothis方法中,p1修改指向实例的num,有 p1->instance (num=20)
可以看出来,p 和 p1都是指向同一个实例,于是 main中 p.num的值也是20
如果希望按引用传递的时候,不相互影响呢,拿上面的例子来说,只要dothis方法中,将引用指向一个新创建的
对象就行了。
class Instance{
public int num = 0 ;
}
public class Test2 {
public void dothis(Instance p){
p = new Instance();
p.num = 20;//4
System.out.println("dothis中num的值是"+p.num);
}
public static void main(String[] args) {
Instance p = new Instance();//1
p.num = 10;//2
Test2 t = new Test2();
t.dothis(p);//3
System.out.println("main中num的值是"+p.num);
}
}
再次分析,程序过程中发生的引用传递:
3,前面两步和上面相同,第三步,同样 有 变量p 和 形参 p1 的值相同,存放的都是instance 实例的地址
此时两个引用指向的都是同一个变量
4. 第四步,dothis方法中, 形参p1指向的是新创建的instance ,p1中存放的是新的对象的内存地址,
main中 变量p 存放的还是原来的 instance 实例地址,这样,输出的结果就是:
dothis 中 num的值是 20 ,main中num的值是 10
结论:
“在Java里面参数传递都是按值传递”这句话的意思是:按值传递是传递的值的拷贝,按引用传递其实传递的是引用的地址值,所以统称按值传递。
在java里面只有基本类型和按照下面方式定义的String是按值传递,其他的都是按照引用传递(集合和数组也是按照引用传递)。按双引号定义的string 是按值传递 String str = "hello world";String[] 也是按引用传递