[英]Counter Intuitive Object Parameter Behaviour
我很清楚Java通过值传递参数,并且由于对象是作为变量保存在变量中作为引用的,因此当值可变时可以更改对象值。 我还了解的是,String类包含不可变的对象。 因此,为了测试我的理解,我决定编写一些代码,该代码将对象作为参数传递给方法,同时更改其字符串和int变量,然后进行打印。 我期望,由于参数只是一个副本,因此这些更改不会影响传入的变量。将对象作为参数传入不会将整个对象复制到新变量中吗? 这与几个消息来源告诉我的情况相反。 这是有问题的代码:
public class Test {
public int testVar = 20;
public String testString = "Hello";
public static void testCheck(Test test){
test.testString = new String("GoodBye");
test.testVar = 10;
}
public void printTest(){
System.out.println("testVar: " + testVar + " testString: " + testString);
}
public static void main(String[] args) {
Test test1 = new Test();
test1.printTest();
testCheck(test1);
test1.printTest();
}
}
输出:
testVar: 20 testString: Hello
testVar: 10 testString: GoodBye
预期:
testVar: 20 testString: Hello
testVar: 20 testString: Hello
提前致谢。
一些概念:
最后一点是您在testCheck
方法中正在做的事情。 也,
将对象作为参数传递不会将整个对象复制到新变量中,而只是传递该对象引用吗?
那句话没有多大意义。 您作为参数传递的是一个值。 该值是对象引用,而不是对象。 在您的方法中,可以取消引用该对象引用以访问字段并调用所引用对象的方法。
在Java中,参数始终按值传递,因此test
实际上是test1
的副本。 您犯的错误是,复制对象变量不会复制对象 ; 它将引用复制到同一对象。 由于您要对同一对象实例上的字段进行突变,因此两个引用都将看到新状态。 相反,当您“更新”一个不可变的对象变量(如String
,您只是在引用一个新的对象实例。
顺便说一句,很少有理由创建new String
而不是仅仅分配字符串文字。 在这种情况下绝对没有。
您正在将引用的副本传递给原始对象。 实际上,您正在传递原始对象的引用,依此类推:
testCheck(test1);
您正在修改test1
对象的属性/变量。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.