Java方法传参真的有引用传递吗?

数据类型

Java中的数据类可以分为两类:基本类型和引用类型。

基本类型包括整型(byte,short,int,long)、浮点型(float,double)、字符型(char)、布尔型(boolean)。

引用类型包括类、接口、数组。

很多介绍Java的文章都会说,Java方法有两种传参方式:值传递和引用传递。

真的有两种传参方式吗?

我们先来看下基本类型和引用类型在内存中是如何存储的。

基本类型

基本类型变量在内存中会直接存储变量的值,比如:int a = 1;
那么a对应的内存单元中存储的就是1。
Java编程之美
(图片来源:王争《Java编程之美》https://www.xzgedu.com/detail/p_625cfab5e4b01a4851f30d8a/6)

引用类型

引用类型变量存的不是对象本身,而是对象所在内存块的首地址。
Student stu = new Student(1,3);
stu作为引用类型的变量,存的是Student对象在内存中的首地址。
在这里插入图片描述
(图片来源:王争《Java编程之美》https://www.xzgedu.com/detail/p_625cfab5e4b01a4851f30d8a/6)

方法传参

如果方法的参数是基本类型,那么调用方法的时候,会把变量在内存中值复制给方法的参数,也就是change(a)方法会把,a在内存中的值1复制一份传给变量x。

因为x是方法change的局部变量,是存在change方法栈中的,并不会影响存在main方法栈中的a变量,所以输出结果是1。

 public static void main(String[] args) {
    
    
        int a = 1;
        change(a);
        System.out.println(a); // 输出结果为1
    }

    public static void change(int x) {
    
    
        x = 2;
    }

如果方法参数是引用类型,那么调用方法的时候,同样会把变量在内存中值复制给方法的参数,也就是change(stu)方法会把,stu在内存中的值,也就是Student对象的首地址,复制一份传给变量stux。

这样变量stu和变量stux在内存中的值都是一样的,都是Student对象的首地址,也就是说变量stu和变量stux的值指向了同一个Student对象。

所以在change方法中变量stux,修改了其所指向对象的属性age,也就是修改了变量stu所指向对象的属性age,因为它们指向的是同一个对象。

 public static void main(String[] args) {
    
    
        Student stu = new Student(1,20);
        change(stu);
        System.out.println(stu.age); // 输出结果为18
    }

    public static void change(Student stux) {
    
    
        stux.age = 18;
    }

    static class Student {
    
    
        int id;
        int age;
        public Student(int id,int age) {
    
    
            this.id = id;
            this.age = age;
        }
    }

总结

总结一下,不管方法的参数类型是基本类型还是引用类型,它们传递都是变量在内存中的值,只是基本类型在内存中的值就是值本身,引用类型在内存中存的是对象的首地址而已。

所以,在Java语言中方法传参,不管是基本类型还是引用类型都是按值传递的,都是传递变量中的值。

那C++为什么有引用传递呢?

因为C++可以通过"&"引用获取到一个变量的地址,它可以将变量的地址传给函数。

随便从网上找了一幅图说明一下:
在这里插入图片描述
C++的引用传递,传的是变量自己的地址:0x7fff5cc109de

Java传递的是变量里的值:10
(如果是引用类型的变量,那么变量里的值就是对象的首地址,不管怎么样,传的都是变量里的值)

所以说Java没有引用传递,只有值传递。

猜你喜欢

转载自blog.csdn.net/zhanyd/article/details/124629099