原文: https://howtodoinjava.com/java/basics/java-is-pass-by-value-lets-see-how/

    关于“java 是按值传递还是按引用传递?”的争论很多。 好吧,让我们最后一次总结一下, Java 是按值传递而不是引用传递。 如果已经按引用传递了代码,那么我们应该能够像对象交换那样使用 C 语言,但是我们不能在 Java 中做到这一点。 我们已经知道了吧?

    当您将实例传递给方法时,其内存地址会一点一点地复制到新的引用变量中,因此它们都指向同一实例。 但是,如果您在方法内部更改了引用,原始引用将不会更改。 如果它按引用传递,那么它也将被更改。

    为了证明这一点,让我们看一下内存分配在运行时如何发生。 如果有任何疑问,它应该可以解决。 我正在使用以下程序演示该概念。

    1. public class Foo
    2. {
    3. private String attribute;
    4. public Foo (String a){
    5. this.attribute = a;
    6. }
    7. public String getAttribute() {
    8. return attribute;
    9. }
    10. public void setAttribute(String attribute) {
    11. this.attribute = attribute;
    12. }
    13. }
    14. public class Main
    15. {
    16. public static void main(String[] args){
    17. Foo f = new Foo("f");
    18. changeReference(f); // It won't change the reference!
    19. modifyReference(f); // It will change the object that the reference variable "f" refers to!
    20. }
    21. public static void changeReference(Foo a) {
    22. Foo b = new Foo("b");
    23. a = b;
    24. }
    25. public static void modifyReference(Foo c) {
    26. c.setAttribute("c");
    27. }
    28. }

    让我们逐步查看运行时发生的情况:

    1)Foo f = new Foo("f");

    该语句将创建Foo类的实例,并将attribute初始化为f。 对该创建实例的引用分配给变量f

    Java 按值传递与按引用传递 - 图1

    2)public static void changeReference(Foo a)

    执行此操作后,将声明名称为a的类型为Foo的引用,并将其最初分配为null

    Java 按值传递与按引用传递 - 图2

    3)changeReference(f);

    调用方法changeReference时,会将引用a分配给作为参数传递的对象。

    Java 按值传递与按引用传递 - 图3

    4)Foo b = new Foo("b");内部第一种方法

    这将与第一步完全相同,并创建一个新的Foo实例,并将其分配给b;

    Java 按值传递与按引用传递 - 图4

    5)a = b;

    这是重点。 在这里,我们有三个参考变量,当执行语句时,ab将指向在该方法内部创建的同一实例。 注意:f不变,它一直指向实例,它原来是指向的。没变 !!

    Java 按值传递与按引用传递 - 图5

    6)ModifyReference(Foo c);

    现在,当该语句执行引用时,将创建c并将其分配给具有属性f的对象。

    Java 按值传递与按引用传递 - 图6

    7)c.setAttribute("f");

    这将更改引用c指向的对象的属性,以及引用f指向的同一对象。

    Java 按值传递与按引用传递 - 图7

    我希望这个解释足够清楚,以使您更好地理解(如果尚未理解)。

    学习愉快!