用Java传递的参数

Sor*_*rin 0 java parameter-passing

我在类中有一个Long对象,我给它一个值,然后我将它传递给另一个类的构造函数,在那里它被更改.为什么第一个对象中的变化不可见?

代码:

public class ClassA {
    private Long t;

    public ClassA() {
        t = new Long(10);
        System.out.println(t); // prints 10
        new ClassB(t); // it is modified (see ClassB)
        System.out.println(t); // prints 10 again
    }

    public static void main(String[] args) {
        new ClassA();
    }
}

class ClassB {
    private Long p;

    public ClassB(Long p) {
        this.p = p;
        this.p = this.p + 1;
        System.out.println(this.p); // prints 11
    }
}
Run Code Online (Sandbox Code Playgroud)

输出为:10 11 10 Long变量在ClassA中初始化.然后我将它传递给ClassB,修改它,并清楚地看到更改在第一堂课中不可见.为什么?

fge*_*fge 6

这是因为Long班级是不可改变的; 一旦创建了一个实例,它就永远不会改变.

在这一行:

this.p = this.p + 1;
Run Code Online (Sandbox Code Playgroud)

你正在做的是创建一个 Long对象.不变类的其它实例包括对原始数字类型(所有"包装"类Byte,Short等)和String.

没有用的是它使+操作员不直观; 什么真的没有帮助的是,语言允许+所有这些不可改变的类.

在上面的行中发生的事情可以写成(尽管在字节码中它的发生方式不同,我怀疑):

long tmp = this.p.longValue();
tmp += 1;
this.p = new Long(tmp);
Run Code Online (Sandbox Code Playgroud)

您还可以通过在课堂上标记p为as final来验证不变性B,这意味着引用 p永远不会改变; this.p = this.p + 1您尝试修改引用时将引发编译错误p.