• Post Reply Bookmark Topic Watch Topic
  • New Topic

Java Pass by value? But List objects change!  RSS feed

 
Natalie Ap
Ranch Hand
Posts: 49
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Hello friends,

I have tried out the following code and noticed that none of the objects or primitive types are passed-by-reference since none of them are altered after a method call.
BUT when a list is passed to a method. Some alterations are done on the list and then the method exits. But in the calling method, if we try to examine the list, it seems to have changed according to the operations within the called method.
Please let me know that if java is pass-byvalue, how come list object gets altered? What is the reason behind this behaviour. Why does the String object not get changed, but the List object gets changed!





Output:
 
James Tharakan
Ranch Hand
Posts: 580
Eclipse IDE
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
return and accept the updated value
 
Natalie Ap
Ranch Hand
Posts: 49
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
James Tharakan wrote:return and accept the updated value


Hi James,

When a List is passed to a method it gets altered when we return to the calling method. But this does not happen with any other object or primitive value. I already know about this behaviour.

My question is, that if java is pass-by-value, why is the behaviour different for a list.

Thanks,
N
 
Paul Beckett
Ranch Hand
Posts: 96
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
java is always pass by value. That is the argument to a method for an object value is actually a COPY of the reference to the object.

Your method:


works because you are adding to the List that is referenced by the parameter l.
Try changing your code around:
(i) add "Hello" to the list defined in your main method
(ii) Modify the change(List) method so instead of adding an value to it create a new list. i.e. "l = new ArrayList<String>()".
(iii) Observe that your output still includes the value "Hello"

The reason it doesn't work for Strings (or wrapper classes) is because they are immutable.
 
Natalie Ap
Ranch Hand
Posts: 49
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Paul Beckett wrote:java is always pass by value. That is the argument to a method for an object value is actually a COPY of the reference to the object.

Your method:


works because you are adding to the List that is referenced by the parameter l.
Try changing your code around:
(i) add "Hello" to the list defined in your main method
(ii) Modify the change(List) method so instead of adding an value to it create a new list. i.e. "l = new ArrayList<String>()".
(iii) Observe that your output still includes the value "Hello"

The reason it doesn't work for Strings (or wrapper classes) is because they are immutable.



Hi Paul!

Thanks for your reply..

But the changes you suggested would obviously work. If i create i completely new list within the change method, the variable now starts pointing to a new reference of the Object. Hence the list appears to have not added anything when we return back to the calling method.

I have been wondering if the list appears to have been changed in the above code, why is this not applicable for any other object! The list object seems to be behaving differently. Of course, like you say String objects are immutable, so are Wrapper objects. But what if we use some other object in place of these immutable objects? Would it behave like the List??

Regards,
N
 
Ernest Friedman-Hill
author and iconoclast
Sheriff
Posts: 24217
38
Chrome Eclipse IDE Mac OS X
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
N Pats wrote: But what if we use some other object in place of these immutable objects? Would it behave like the List??


Yes. Try the same kind of thing with any array object, for example, or a HashMap, or a JButton, or a DecimalFormat, or any of the many other API classes that have state that can change. Or write a class yourself, and try using that.
 
Campbell Ritchie
Marshal
Posts: 56530
172
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
You have got it, well 99%.

You cannot change which object you are working with; when your method finishes, whichever object was pointed to by the value passed is the same object. Since Lists (like most objects, not String or Boolean or the Number classes) have methods which allow you to alter the state of the object, you can call those methods and manipulate the object.

But the actual object you were manipulating is still the same object. You can create new objects inside your method, or re-assign the parameter, but the object which was in the original reference is still the same object as before.
 
Paul Beckett
Ranch Hand
Posts: 96
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
The modification to the list were just to bring it in line with the way you were handling the change(Integer) method. You weren't treating the Integer and the List the same so it was an unfair comparison.

Can you modify a mutable object? Its better for you if you try it and let us know what you find out.


 
Sunil Kumar
Ranch Hand
Posts: 81
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Java copies and passes the reference by value, not the object. If you pass a reference that is pointing to an object, the changes done to the object (through reference copy) will remain to that object. But as both the actual reference and the copy passed are pointing to the same object, the changes are reflected back after the method is finished.

Further this holds true for all Type, not only lists.
 
Sunil Kumar
Ranch Hand
Posts: 81
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Before method A : referenceA points to ObjectA
Passing to method : referenceB is created pointing to objectA
In Method : referenceB points to ObjectA (unless you assign a whole new object to the referenceA)
you make changes to ObjectA
Out of method now : referenceA still points to ObjectA . Hence changes in ObjectA are reflected back.

Think diagrammatically in terms of allocation.
 
Natalie Ap
Ranch Hand
Posts: 49
  • Mark post as helpful
  • send pies
  • Quote
  • Report post to moderator
Sunil Kumar wrote:Before method A : referenceA points to ObjectA
Passing to method : referenceB is created pointing to objectA
In Method : referenceB points to ObjectA (unless you assign a whole new object to the referenceA)
you make changes to ObjectA
Out of method now : referenceA still points to ObjectA . Hence changes in ObjectA are reflected back.

Think diagrammatically in terms of allocation.



Hello All,

Thanks a lot for your replies. It helped me understand the concept.

I tried using a mutable object for the change method and it worked like the list!

Thanks,
N


 
  • Post Reply Bookmark Topic Watch Topic
  • New Topic
Boost this thread!