Reputation: 1882
i would like to ask, where is the difference between two examples:
class PassA
{
public static void main(String [] args)
{
PassA p = new PassA();
p.start();
}
void start()
{
long [] a1 = {3,4,5};
long [] a2 = fix(a1);
System.out.print(a1[0] + a1[1] + a1[2] + " ");
System.out.println(a2[0] + a2[1] + a2[2]);
}
long [] fix(long [] a3)
{
a3[1] = 7;
return a3;
}
}
in code above:
but in code below
class Test
{
public static void main(String [] args)
{
Test p = new Test();
p.start();
}
void start()
{
boolean b1 = false;
boolean b2 = fix(b1);
System.out.println(b1 + " " + b2);
}
boolean fix(boolean b3)
{
b3 = true;
return b3;
}
}
Question
What is the difference?And how can I change code (example 1 ) so a1
won´t be changed?
Upvotes: 0
Views: 151
Reputation: 4111
In Java everything is passed by value (see here).
Basically, there are three cases of variables passed to a function:
for the first two cases, the contents are not altered (e.g. your example 2 passing a boolean)
in the third case, the contents can be altered (e.g. your example 1 passing a long[]).
So, how not to alter your long[] in example 1? It is not possible with primitive arrays (except if you create another array inside the function using a for loop for copying all the items of the input to this new array and then make your operations to this copy). Or create a copy of the initial array before calling the function and invoke the function with this copy as input.
Apart from copying all the contents to another array, immutable native primitive arrays do not exist. You'll need to use a List or some other data structure:. You'll need to use a List or some other data structure (see here)
Upvotes: 1
Reputation: 3377
Java passes in by value, meaning only a copy of the original is passed into the method. However, here's the difference:
Refer to the below classical bad-swap example:
public void badSwap(int var1, int var2)
{
int temp = var1;
var1 = var2;
var2 = temp;
}
Here, it's a badSwap because var1 and var2 are left unchanged. Only copies of those integers are swapped within the function.
Now, when a copy is made of your 'al' array reference in your example, the copy of 'al' still refers to your original {3, 4, 5} array.
Thus, when you do the following:
long [] a1 = {3,4,5};
long [] a2 = fix(a1);
a3[1] = 7 in the fix(al) method changes the value of the original al.
Instead, pass in a copy of the array itself.
Points to remember:
A copy of a reference still refers to the same thing, whereas a copy of a primitive type (int, boolean..) is completely separate from the original.
Upvotes: 0
Reputation: 280132
Drawings
a1 => Long object ID 9999: [3, 4, 5]
a3 => Long object ID 9999: [3, 4, 5] (ie. same object)
You then do
a3[1] = 7;
we dereference a3
and get
Long object ID 9999: [primitive long value: 3, primitive long value: 4, primitive long value: 5]
we then access element at index 1 and change its value to 7
Long object ID 9999: [primitive long value: 3, primitive long value: 7, primitive long value: 5]
In the second case
b1 = primitive boolean value: false
b3 = primitive boolean value: false (no relation to the other, just another false)
You then do
b3 = true;
this changes only b3
b3 = primitive boolean value: true (still no relation)
This is because Java is a pass-by-value language.
To change your first snippet, you'd have to make a copy of the array and pass that copy when invoking the method.
Upvotes: 1
Reputation: 726909
In Java everything is passed by value, including object references. In both cases a copy of the parameter a3
or b3
is made. However, a copy of an object reference continues referring to the same object, while a copy of a primitive becomes completely disconnected from the original.
To make the first example behave like the second one, create a copy of your array (which is a reference-type object) prior to modifying it:
long [] fix(long [] a3)
{
long[] res = Arrays.copyOf(a3, a3.length);
res[1] = 7;
return res;
}
Upvotes: 1