重点
java中是没有指针的,java中只存在值传递, 然而我们经常看到对于对象(数组,类,接口)的传递似乎有点像引用传递,可以改变对象中某个属性的值。但是不要被这个假象所蒙蔽,实际上这个传入函数的值是对象引用的拷贝,即传递的是引用的地址值,所以还是按值传递。
代码示例:
public class Test {
public static void main(String[] args) {
int a = 10;
int b = 20;
change(a,b);
System.out.println("a="+a+" b="+b);
Student s = new Student("张三");
Student t = new Student("李四");
change(s,t);
System.out.println("s="+s.name+" t="+t.name);
Student s1 = new Student("张三");
Student t1 = new Student("李四");
change1(s1,t1);
System.out.println("s="+s.name+" t="+t.name);
}
public static void change(int a,int b){
int c = a;
a=b;
b=c;
}
public static void change(Student a,Student b){
Student c = a;
a=b;
b=c;
}
public static void change1(Student a,Student b){
Student c = new Student();
c.name = a.name;
a.name = b.name;
b.name = c.name;
}
}
class Student {
String name;
Student(){}
Student(String name){
this.name = name;
}
}
解析:
1、在int类型的change方法中,传入方法中的a和b是形参,会在栈内存中申请独立的空间a'和b'
,在方法中又会申请一个c,在方法执行完毕之后,a' b' c都会被回收掉,并不会影响a和b的值;
2、在Student类型的change方法中,传入方法的Student a和b都是复制了s和t的地址,并不是s和t的对象,
也就是说:s和a指向同一个对象,t和b指向同一个对象,在方法体中的操作只是给a和b的指向替换了一下,
方法执行完毕之后,a、b、c都会被回收,所以不会影响s和t的值
3、与2一样,a和b都是复制了s和t的地址,在方法体中的操作是把a和b的name属性改了,因为s和a指向同一个对象,t和b指向同一个对象,
也就是说s和t的name属性也会随之发生改变。方法体执行完毕之后,a、b、c被回收,但是s和t的值已经发生了改变
图示: