discussing some technical aspects covering tools, frameworks, technologies etc (the areas where i m involved and getting experienced) - feel free to discuss!
Thursday, September 13, 2007
Pass by Reference for object references holds good really?
Pre-requisite: Well, If you want to refreshwith the concepts of "Pass-by-value Vs Pass-by-reference", you may please refer this previous entry in this blog.
With respect to Java, it "passes everything by value". I repeat, "everything" by value only.
Generally, we may think that passing by values will hold good only for primitive types and values but not for the object references.
This everything includes even the references to objects.
Lets say, you have a method which takes an object as a parameter as follows
public void doChange(MyClass myClassObj)
And you call that method from some other piece of code as follows
public void method1()
MyClass myClassObj = new MyClass();
The reference variable myClassObj is being assigned to an object of class MyClass in Heap. Just like primitive variables holding bit patterns to represent a value, reference variables also store the bit patterns to reach an object.
Once you call the method doChange() by passing the reference variable "myClassObj" to it, the value of the bit patterns held by "myClassObj" is being copied and passed into the called method doChange(). In the called method doChange(), the copied-and-sent bit pattern is received in the same name as that of the original reference variable "myClassObj". But the compiler treats that as a different one just like primitives.
Lets say the received reference variable as "myClassObjLocal" for easy understanding. In this stage, both the original refernece variable "myClassObj" and the received reference variable inside the doChange() method "myClassObjLocal" (to compiler) point to the same object in Heap.
Now if you change the state of the object being pointed by, it will reflect to both the reference variables because both of them point to the same object in Heap. Whereas,if you change the received reference variable "myClassObjLocal" to point to a new object (reassign a different object), it does NOT reflect back to the original object because the bit pattern to the "myClassObjLocal" alone gets changed!
If you are clear with the above paragraphs, lets go to an example to make it more clear.
Lets take a small example.
intValue = 1;
public static void changeStateOfObject(TestObjRef obj)
obj.intValue = 2;
public static void changeReference(TestObjRef obj)
obj = new TestObjRef();
obj.intValue = 9;
public static void main(String args)
TestObjRef obj1 = new TestObjRef();
System.out.println("obj1.intValue (1) = "+obj1.intValue);
System.out.println("obj1.intValue (2) = "+obj1.intValue);
System.out.println("obj1.intValue (3) = "+obj1.intValue);
Running the above code produces the following output:
obj1.intValue (1) = 1
obj1.intValue (2) = 2
obj1.intValue (3) = 2
This is because, changeStateOfObject() method just changes the value of the variable "intValue" which definitely constitutes the state of object. And as such, both the "obj1" in main() method and "obj" in changeStateOfObject() method point to the same object. Means, they both hold the same bit patterns to reach a single object of TestObjRef class in heap.
That's why the output in the second line shows the changed state of object "2" as the value of "intValue" property.
If you look at the changeReference() method, by the time of receiving the argument, both the "obj1" reference variable in main() method and received reference variable "obj" in changeReference() method both hold the same bit patterns to reach the same and single TestObjRef class in Heap.
But inside the method, the received "obj" reference variable is reassigned to a newly created object of TestObjRef class. In this case, only the bit pattern of the "obj" reference variable inside the changeReference() method is changed and the change is NOT reflected back to the originally sent reference variable "obj1".
That's why the third line in the output still shows the value of "intValue" as "2" since the changed value "9" is only reflected in the received local reference variable "obj" in changeReference() method.
The received argument (object reference variable) is treated local to the method. That means, the scope of the variable is only local to the called method just like primitives and the variable cannot be accessed outside the method.