编程语言
首页 > 编程语言> > Java中值传递的深入思考

Java中值传递的深入思考

作者:互联网

值传递的思考

值传递还是引用传递

任何一篇文章都会坚定地回答:值传递
但是,当看到这样一段代码时,也许你会有疑问:

	public class TestClass {

    public static void main(String[] args) {
        TargetClass origin = new TargetClass();
        origin.name = "Yan Yu";
        System.out.println(String.format("原本的信息是:%s",origin.name));
        changeAndSayName(origin);
        System.out.println(String.format("现在的信息是:%s",origin.name));
    }

    public static void changeAndSayName(TargetClass obj){
        obj.name = "123";
    }
}

执行结果:

原本的信息是:Yan Yu
现在的信息是:123

哎?不是说好的值传递么?怎么副本传进方法以后,修改字段,原对象的字段也跟着变了?这传进来的难道不是指针吗?

到底什么叫值传递,什么叫引用传递

在搞清楚问题之前,我们有必要严格说明一个问题:
什么叫值传递,什么叫引用传递。
对于Java而言,其实根本就没有什么值传递、引用传递的概念,因为Java就没有指针这个东西,到底是什么传递毫无意义。
只有在和C++/C语言作对比的时候,才有必要说明值传递和引用传递。

如果只从字面意义理解,值传递就是“传递值”,引用传递就是“传递引用”。如果从“无法传递引用,因为Java没有指针”这个角度来理解,Java就确实是值传递,因为没有指针。
但是这没法解释上面那段代码的问题,为什么值变了?

因为Java认为你是把对象的引用当做值传进去了

还是对比C++理解。C++说的引用传递,是在只需要指针的情况下,就可以对某个内存区块进行操作,如果一定要用java的形式写出来,应该是这样:

public class TestClass {

    public static void main(String[] args) {
        TargetClass origin ;
        // 下面一行代码肯定报错,因为java不能取地址
        changeAndSayName(&origin);
        System.out.println(String.format("现在的信息是:%s",origin.name));
    }

    public static void changeAndSayName(TargetClass* obj){
        obj = new TargetClass();
        obj.name = "123";
    }
}

直接对实例操作内存,甚至无需原本的对象初始化
Java能不能做到?做不到。也就是说Java的值传递是相对于直接操作内存而言的。上述例子中实例的值也发生了改变,但从本质上说,你没有操作内存(你没有指针),是JVM操作的。

所以,Java就是值传递,但是是可以影响内存(通过JVM)的值传递。

标签:origin,Java,name,传递,引用,思考,中值,public
来源: https://blog.csdn.net/qq_39203889/article/details/112199095