Java passe-t-il vraiment des objets par valeur? [dupliquer]

Double Possible: est Java pass par référence?

public class myClass{
    public static void main(String[] args){
        myObject obj = new myObject("myName");
        changeName(obj);
        System.out.print(obj.getName()); // This prints "anotherName"
    }
    public static void changeName(myObject obj){
        obj.setName("anotherName");
    }
}

je sais que Java passage par valeur, mais pourquoi faut-il passer obj par référence dans l'exemple précédent, et de les modifier?

20
demandé sur Community 2011-10-25 21:44:29

6 réponses

Java passe toujours les arguments par valeur, pas par référence. Dans votre exemple, vous passez encore obj par sa valeur, pas la référence elle-même. Dans votre méthode changeName , vous assignez une autre référence (locale), obj , au même objet que vous lui avez passé comme argument. Une fois que vous avez modifié cette référence, vous modifiez la référence originale, obj , qui est passée en argument.


EDIT:

permettez-moi de l'expliquer par un exemple:

public class Main
{
     public static void main(String[] args)
     {
          Foo f = new Foo("f");
          changeReference(f); // It won't change the reference!
          modifyReference(f); // It will change the object that the reference refers to!
     }
     public static void changeReference(Foo a)
     {
          Foo b = new Foo("b");
          a = b;
     }
     public static void modifyReference(Foo c)
     {
          c.setAttribute("c");
     }
}

je vais vous expliquer ceci par étapes:

1-déclarer une référence nommée f de type Foo et l'attribuer à un nouvel objet de type Foo avec un attribut "f" .

Foo f = new Foo("f");

Enter image description here

2-du côté de la méthode, une référence de type Foo avec un nom a est déclaré et il est initialement assigné à null .

public static void changeReference(Foo a)

Enter image description here

3-comme vous appelez la méthode changeReference , la référence a sera assignée à l'objet qui est passé comme argument.

changeReference(f);

Enter image description here

4-déclarant une référence nommée b de tapez Foo et l'attribuer à un nouvel objet de type Foo avec un attribut "b" .

Foo b = new Foo("b");

Enter image description here

5- a = b renvoie la référence a et non f à l'objet dont l'attribut est "b" .

Enter image description here


6- comme vous appelez modifyReference(Foo c) méthode, un la référence c est créée et assignée à l'objet avec l'attribut "f" .

Enter image description here

7 - c.setAttribute("c"); va changer l'attribut de l'objet qui se réfère c points à elle, et c'est le même objet qui se réfère f points à elle.

Enter image description here

j'espère que vous comprenez maintenant comment passer des objets comme arguments fonctionne en Java:)

88
répondu Eng.Fouad 2012-06-13 18:41:39

en Java, un objet handle, ou l'identité d'un objet est considéré comme une valeur. Passer par la valeur signifie passer cette poignée, pas une copie complète de l'objet.

Une "référence" dans le terme "passage par référence" ne signifie pas non plus "référence à un objet". Il signifie "référence à une variable "– un" seau " nommé dans une définition de fonction (ou, plutôt, un cadre d'appel) qui peut stocker une valeur.

passer par référence signifierait que la méthode appelée pourrait changer valeurs variables dans la méthode d'appel. (Par exemple, dans la bibliothèque standard C, la fonction scanf fonctionne de cette façon.) Ce n'est pas possible en Java. Vous pouvez toujours modifier les propriétés d'un objet – elles ne sont pas considérées comme faisant partie de sa" valeur". Ce sont des objets indépendants complètement différents.

9
répondu millimoose 2011-10-25 17:53:27

vous changez une propriété de obj , ne changeant pas obj (le paramètre) lui-même.

le point est que si vous pointez obj à quelque chose d'autre dans changeName que que changement ne se refléterait pas dans main .

Voir ce post pour plus de précisions.

2
répondu Dave Newton 2017-05-23 11:54:59

il n'a pas changé obj (votre code ne le change pas de toute façon). Si elle avait été transmise par référence, vous auriez pu écrire:

public static void changeName(myObject obj){
    obj = new myObject("anotherName");
}

et avoir" un autre nom " imprimé par la méthode principale.

2
répondu Maurice Perry 2011-10-25 17:53:42

Java transmet une copie de ce que vous transmettez à votre fonction. Quand c'est un type primitif, il sera la copie d'une valeur. Quand c'est un objet - vous passez la copie de référence. Dans votre exemple de code, vous modifiez l'une des propriétés des objets, mais pas la référence elle-même, de sorte que le nom sera modifié. Cependant, lorsque vous souhaitez assigner un nouvel objet à une variable obj dans la fonction changeName, alors vous changez la référence, donc hors obj aura une ancienne valeur.

1
répondu mmatloka 2011-10-25 17:53:49

il passe la référence à obj comme une valeur (un peu confus je sais :)).

donc disons qu'il fait une copie du pointeur à la valeur d'obj et passer cela.

cela signifie que vous pouvez faire des choses comme:

  public static void changeName(myObject obj){    
        obj.setName("anotherName");
        obj = new myObject();
    }

et la mention

System.out.print(obj.getName());

va toujours se référer à l'ancien objet (celui que vous avez fait setName).

0
répondu Mikel 2012-06-13 19:04:53