代码之家  ›  专栏  ›  技术社区  ›  Jonathan

Java真的总是复制传递给方法的所有对象吗?[副本]

  •  0
  • Jonathan  · 技术社区  · 9 年前

    Java是按值传递的。这意味着被调用的方法作用于传入对象的副本,而不是原始对象。

    如果在方法中未更改对象,则似乎不需要创建实际副本。因此,实现程序以创建这样一个副本的编译器将非常低效。所有Java编译器(javac、gcj、ECJ等)真的都这么做了吗?

    至少在声明参数的情况下 final 不抄袭是有道理的。

    编辑

    好的,所以不会复制对象。我很困惑,因为 String 它的特殊之处在于它是复制的(不可变的)。对我的未知感到抱歉。为了弥补这一点,下面是传递对象时发生的第一千个例子:

    import java.lang.System;
    
    class C { int member; }
    
    public class Test {
        static void subMethod(C object) { object.member=1; }
    
        public static void main(String[] args) {
            C object = new C();
            object.member=0;
            subMethod(object);
            System.out.println(object.member);  // prints "1"
        }
    }
    
    2 回复  |  直到 9 年前
        1
  •  3
  •   BlueMoon93    9 年前

    是的,Java总是按值传递的。但对于对象,它会传递参考值。换句话说,对象不会被复制,但它的引用会被复制。在方法内部更改对象的属性也会在方法外部更改对象。

    从…起 here ,

    但是,对象不是通过引用传递的。正确的语句应该是对象引用按值传递。

    关于主题: 编译器只需将引用复制到堆栈中的内存块。

        2
  •  2
  •   jonk    9 年前

    Java中的对象是引用,通过值传递的就是这个引用;这意味着Java是通过引用传递对象的,用于实际目的。

    编辑

    我对“实际目的”一词的使用似乎引起了很多争议,所以让我澄清一下。我的意思是,当大多数人想到“通过引用传递”时,他们想到的是对传入值的更改是在该方法之外持久化的,Java就是这样。例如

    void someMethod(SomeClass a) {
        a.mutateState();
    }
    SomeClass a = new SomeClass();
    someMethod(a); //passes reference to a by value; 
    a.methodInvolvingSomeState(); //mutations of object state persist to here, as if the previous call were pass-by-reference.
    

    这就是我所说的“出于实际目的”;OP的印象是 a 我想解释的是事实并非如此。我完全知道java是 总是 通过值传递,因此显式声明它是通过值传递的引用。正如评论中所指出的,在很多情况下,情况与实际情况不同 事实上 通过引用,我并不打算指出这些在Java中都是可能的。