Question

Lets get the terminology straight once and for all. I have been confused about all the conflicting vocabulary online relating to passing by reference and value.

Below is an easy clean example of passing an object argument to a method. The result is that Mike Grant's name is butchered as well as his age. So the underlying object was changed.

2 Major questions:

  • What is the value, and what is the reference?
  • Would the hashcode be different of p1 once the changePersonObject() method is run on it?

My code:

public class App {      
    public void changePersonObject(Person p){
        p.setAge(100);
        p.setFirstName("Lost");
        p.setLastName("Boy");
    }

    public static void main(String[] args) {            
        App a = new App();
        Person p1 = new Person("Mike", "Grant", 24, 180);               
        a.changePersonObject(p1);
        System.out.println(p1); // person objects name is changed to "Lost"
    }
}
Was it helpful?

Solution 2

The expression

Person p1 = new Person("Mike", "Grant", 24, 180);               

creates a new object of type Person and assigns the value of its reference to the variable p1.

Java is pass by value. That means that a copy of the value used as an argument is bound to the parameter of the method.

The expression

a.changePersonObject(p1);

is passing p1 as an argument to the invocation of the changePersonObject method. A copy of the value of p1 which is the reference to an object is therefore bound to the parameter p in

public void changePersonObject(Person p){
    p.setAge(100);
    p.setFirstName("Lost");
    p.setLastName("Boy");
}

In the method itself, p is referencing the same object as p1 in main. So when you dereference it by invoking a method such as

 p.setAge(100);

you're affecting the same object.

If instead you did

p = new Person("Soto", "Deli", 24, 42);// whatever arguments

The variable p now has a new value, the value of the reference to a new Person object. This will not affect p1 in main in any way.

would the hashcode be different of p1 once the changePersonObject() method is run on it?

If you haven't implemented a hashcode method in Person, then the value returned will be the same regardless of you changing the value of the instance's fields.

OTHER TIPS

Java is pass-by-value indeed, but actually the one that hold this value is little bit of different with what you might think of. java is pass by value?
the word value, which in basic data type is the data itself, for instance

int numberA=100  ;
int numberB=numberA;

the value that passed from numberA to numberB is the data 100.
things never change in Reference type:

Person p = new Person("Lost", "Boy", 24);
Person person=p;
person=new Person("Rugal", "Bernstein", 23);

the value that is passed from p to person is the reference address that point to the Person("Lost", "Boy", 24) one, for any details please execute program above and debug it yourself to clarify them.
Here you might think, after person=new Person("Rugal", "Bernstein", 23); the value of person now is disparate with its original one. yes of course, now if you println(person) and that will turn out to be a new Person as you might think of.
But what about p, does that changed because Java is pass-by-value?
Actually, after test with that, I found it is not, even if you changed the person, it will not bother p. what's wrong with java, is there any problem here ?

Yes, java demonstrated there is no pointer in it and all the things that passed in parameter is called reference. lets go back to C/C++ style of programming:

int data=100,temp=50;
int* pdata=&data;
int& rdata=data;

pdata=&temp;
println("%d  %d",*pdata,rdata);

rdata=temp;
println("%d  %d",*pdata,rdata);

anything special can you find from above?
yes, actually in C/C++ , there is two type of so call pass-by-value method, the first one declared by * is called pointer, second one start with & named reference, here please do not consider this reference with java, because you will find they are different later.
in C/C++ , the reference is a kind of alias, in other word, these two variables are totally identical thing, whatever changes you made on one will thus effect the other one. because they are just one thing.
But Pointer is a little different with reference. yes pointer can also point to a variable and you can also change the value of that variable by using *pdata=temp. But here is a problem, when you using pdata=&temp to change the pointer itself, will the data change according to pdata?
the answer is NO!
you can test it yourself ! because what value store in pointer is the address of data variable, when you want to change the value of data it can surely change it by refer *, but when you try to change the address that stored in pdata it would not bother with data because they are totally different two variable.
Now do you have a familiar sense that you have ever feel this before?

yes, in java the so called reference is what pointer behave like in C/C++.

and here we have the deal, in java that demonstrated itself with pass-by-value is correct and no more pointer is a mendacity.

now let me answer questions:

1.the word value is the data that stored in memory. in java primitive type hold real data as value and address as value in reference type.

2.as I have already explained above, you can test it yourself!

3.and I tested some code, the hashcode() will not change so long as the value of your object do not change.
for instance:

Person p = new Person("Lost", "Boy", 24);//Hash Code 38443066
p.setAge(100);  //Hash Code 38443066
p=new Person("Rugal", "Bernstein", 23);//Hash Code 38444526

because in default situation, hashcode() method only measure the address itself hence so long as your address unchanged, the hashcode() will not change.
you can override this method by yourself to measure its member fields as well.
the method changePersonObject() only changed the member field in it thus will have no difference with outer hashcode(). you can achieve it by person=new Person("Rugal", "Bernstein", 23); in this method, its hashcode() will surely changed.

please try it and you will get more comprehension with Java

Java only supports pass by value, not pass by reference. (References to objects are passed by value). For more information please see the following: http://javachannel.net/wiki/pmwiki.php/FAQ/PassingVariables, http://www.javaworld.com/javaworld/javaqa/2000-05/03-qa-0526-pass.html, and http://javadude.com/articles/passbyvalue.htm?repost

  1. p1 = new Person("Mike", "Grant", 24, 180); <-- the "value" of the Object person is the Object, p1 is the "reference" to that Person object
  2. Yes. If Person implements hashCode() correctly.

The problem is that when comparing with other languages, the meaning of pass by value and pass by value is slightly different.

In your example, the fact that you can change the values of p1 in a method may make you believe that you are passing by reference - this is not the case in Java.

To illustrate, that this is passing by value

public class App {

public void changePersonObject(Person p){

    p = new Person("Lost", "Boy", 24, 100);  
}

public static void main(String[] args) {

    App a = new App();
    Person p1 = new Person("Mike", "Grant", 24, 180);               
    a.changePersonObject(p1);
    System.out.println(p1); // person objects name is still "Mike"
 }
}

Unless we can see how the hashcode is generated, then it is impossible to answer the second question. If it is not implemented in Person, then it is likely that the value returned will be the same regardless of you changing the value of the instance's fields.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top