This question already has answers here:
Closed 10 years ago.
Possible Duplicate:
Is Java “pass-by-reference”?
if we have big byte[] array (like 40Mb) and we want to send it in method
method(array);
will the array be copied? So memory will increase by another 40Mb in Java env => 80Mb, right?
If yes, how can we destroy the 'first' array after calling the method?
No, the array will not be copied.
In Java, everything is always passed by value.
Variables of non-primitive types are references to objects. An array is an object, and a variable of an array type is a reference to that array object.
When you call a method that takes a non-primitive type parameter, the reference is passed by value - that means, the reference itself is copied, but not the object it refers to.
No new Object will be created, Just a reference will be copied to function parameter.
The variable array is actually just a reference to the array object. When you pass array to a function you are just copying the reference not the actual array the the reference refers.
Java is always pass by value. The value being passed is the value of the variable in the case of a primitive type and the value of the reference held by a variable in the case of an Object.
In this case, an array is an Object and what is passed by value is the reference to that Object. So no, the array will not be copied.
No, the array will not be copied. In fact, because:
In Java, everything is always passed by value.
Array itself is a object.
So, the result is array' will be copy for method, but the thing it contains: bytes elements DOES NOT copy. so, everything you change for array in the method will affect the original array.
So, memory will not double as you see :)
Related
enter image description hereWhen I'm learning array's knowledge, there are such descriptions saying array holds reference variables(not object itself) or primitives, as opposed to ArrayList holding an object. I want to confirm why ArrayList can hold object rather than reference variables. enter image description here
You're just taking everything out of context...
if you would read further in the second image then you'd understand that there exists primitve arrays (int[]) but no such thing as a primitive List (List<int>).
Instead you have to use wrapper classes (List<Integer>).
Then don't mess up the definition of Object and Object reference because in java you never can have an Object in place, you're always working with Object-references (and also with primitives to be really clear).
I'm working on some code and trying to figure out how to copy an object reference to another object. I keep seeing the clone() method used, but I've read it's flawed and the class I'm wanting to copy is already implementing serializable. So one question I have is about the difference between using '=' and the clone method - My understanding is that both of these are shallow copies so they should work the same, but if that's true, then what is the benefit of having a method for this?
The code I'm working on has 2 arrays of objects - both the same type of object, all objects in both arrays are initially null, and I assign the values of array B to equal array A.
As the code progresses objects in array A are initialized and values are assigned to the variables of the objects in array A.
At the end of the code though, all objects in array B are still null.
Do I have the concept wrong here?
If the concept isn't wrong I assume it's just something I'm overlooking in my code.
Any help is appreciated.
I'll make my comment an answer:
Your question is comparing apples to oranges, they are so completely different that they can't be compared. = assigns a reference, that's it. Clone creates a completely new object, one whose state should be the same as the cloned object, but again it is a completely different object/reference. As an aside, there are deep and shallow clones, and so the composite fields of shallow copied clones may be identical, but that's the subject of another question.
When you use =, you copy the reference of the object (in memory). When using .clone(), you create a new object.
This question already has answers here:
Is Java "pass-by-reference" or "pass-by-value"?
(93 answers)
Are arrays passed by value or passed by reference in Java? [duplicate]
(7 answers)
Closed 9 years ago.
I have trouble with scope of variable.
public static void main(String[] args){
int[] test={1,2,3};
test(test);
System.out.println(test[0]+" "+test[1]+" "+test[2]);
}
static void test(int[] test){
test[0]=5;
}
I expected the output to 1 2 3, but the result was 5 2 3.
Why I changed the value in the array in the method, but the original array changed?
An array in Java is an object. When you create an array via new, it's created on the heap and a reference value (analogous to a pointer in C) is returned and assigned to your variable.
In C, this would be expressed as:
int *array = malloc(10 * sizeof(int));
When you pass that variable to a method, you're passing the reference value which is assigned (copied) to the local (stack) variable in the method. The contents of the array aren't being copied, only the reference value. Again, just like passing a pointer to a function in C.
So, when you modify the array in your method via that reference, you're modifying the single array object that exists on the heap.
You commented that you made a "copy" of the array via int[] temp=test ... again, this only makes a copy of the reference value (pointer) that points to the single array in memory. You now have three variables all holding the same reference to the same array (one in your main(), two in your method).
If you want to make a copy of the array's contents, Java provides a static method in the Arrays class:
int[] newArray = Arrays.copyOf(test, test.length);
This allocates a new array object on the heap (of the size specified by the second argument), copies the contents of your existing array to it, then returns the reference to that new array to you.
Definitions:
Reference = A variable that points to the location in memory where your array lives.
Value of a Reference = The actual memory address location itself
You passed the value of the reference of your array into your test() method. Since java is Pass By Value, it passes the value of the reference, not the value of your array (ie. a copy).
It may be easier to think of a reference as a pointer if you have a C background. So a value of a reference is essentially it's memory address (I'm fudging java rules here but it may be simplest to think of it this way)
So, in your example, you pass the value of the reference which points to your array, into your test() method, which then uses that reference value to lookup where your array is in memory, so it can access data in your array.
Since in your test() method you do not change your array's reference (where it points to, ie. test = new int[10];), then your test() method acts on the original data in the array (because it still points to your original array's location), leading to element 0 being set to a value of 5.
This question already has answers here:
Are arrays passed by value or passed by reference in Java? [duplicate]
(7 answers)
Is Java "pass-by-reference" or "pass-by-value"?
(93 answers)
Closed last month.
When I write like this:
public class test {
void mainx()
{
int fyeah[] = {2, 3, 4};
smth(fyeah);
System.out.println("x"+fyeah[0]);
}
void smth(int[] fyeah)
{
fyeah[0] = 22;
}
}
It prints x22;
When I write like this:
public class test {
void mainx()
{
int fyeah = 5;
smth(fyeah);
System.out.println("x"+fyeah);
}
void smth(int fyeah)
{
fyeah = 22;
}
}
It doesn't print x22, but prints x5.
Why, in the second version function, doesn't the value change? Does it change values only for array elements?
The fyeah variable in your first example contains a reference to an array (not an array), while the fyeah integer in your second example contains an integer.
Since Java passes everything by value the following will happen:
In the array case: A copy of the array reference will be sent, and the original array will be changed.
In the int case: A copy of the integer will be changed, and the original integer will not be changed.
It's because your int is a primitive and the method smth creates a local copy which is why it doesn't print the way you want. Objects are passed by value as well, but a value to the pointer in memory. So when it is changed, the pointer stays throughout both methods and you see the change. Read More Here
Ok. An int in java ( and really all languages that have strict data typing ) is a primitive data type. Its just a single variable of that data type. In java this means its passed by value to the method. So when you pass in the argument, a copy of the passed variable is created. Any operations that take place in the method act on that copy not the passed variable.
Actually in java EVERYTHING is passed by value but getting into the details of how that actually is true with what I am going to say next seems inadvisable.
With the array...its a collection of variables of the primitive data type int. So an entire copy of the array isn't actually made just a copy of the reference to the memory that stores the array. so yes the value of the int IN the array is changed from operations in the method.
In short methods don't change the external value of primitives (int,float,double,long,char) with the operations in the method, you have to return the resulting value of those operations to the caller if you wish to obtain it. Operations do change the value with most objects as well as with arrays of primitives. Hope that helps. Really unsure of how low level to get. Maybe someone else can clearly explain exactly why its by value. I "get" it but find it hard to help other people understand.
Think it in terms of memory: Lets analyse your first program -
In mainx , fyeah is an array of ints , so its a reference ( or a pointer if I may ). This reference points to a location in heap memory where the actual array of ints is stored. Lets say at address 100. Located contiguously from here are three ints ( lets say beginning at address 100 , 104 and 108 respectively are 2 ,3 and 4 ).
Now you call your method smth and pass the reference. Within the method , there is another reference ( of an int array type ) named fyeah. This fyeah is quite distinct from fyeah reference in the mainx method. Now , when you call smth and pass the fyeah from mainx , the fyeah within the smth method is initialized to point to the same location ( ie memory address 100 )
When you access the 0 element of fyeah and assign it a value of 22 , it reaches out to the memory location of 100 and writes this value 22 there. When you come back in your mainx method , the fyeah reference is still referring to memory address 100. But the value present at that location is now 22. So you get that value when you access the first element from fyeah in mainx.
Now , your second program. Your mainx method declares an int ( not an array , but a simple int ) and set it to 5. This fyeah variable is created on stack not on the heap. The value of 5 is stored on the stack. Now you call smth and pass this variable. Within the method smth , you again declare an int variable , fyeah by name ( as a formal method argument ). Again this is distinct from the fyeah of the mainx method and this fyeah is also created on stack.This variable will be initialized to a value of 5, copied over from the fyeah you passed to smth as argument. Note now that there are two distinct copies on fyeah variables , both on stack , and both a value of 5. Now you assign the fyeah in smth a value of 22. This will not affect the fyeah of the mainx method,so when you return to mainx and access fyeah , you see 5.
The int is a value type so 5 is passed directly into smth which can only modify the local copy. An array on the other hand is a reference type so the elements of that array can be modified.
Seeing it a bit less technically, I would say that
fyeah[0] = 22;
is changing the content of (the object pointed to by) fyeah, while
fyeah = 22;
is changing (the variable) fyeah itself.
Another example:
void smth(Person person) {
person.setAge(22);
}
is changing (the content of) the person while
void smth(Person person) {
person = otherPerson;
}
is changing the variable person - the original instance of Person is still unchanged (and, since Java is pass-by-value, the variable in the calling code is not changed by this method)
When adding an object to a data structure the reference to the object is always added, not the object itself. So below code snippets are fundamentally the same ?
Snippet 1 -
Object objectRef = new Object();
Vector vector = new Vector();
vector.add(objectRef);
Object object = (Object)vector.get(0);
Snippet 2 -
Vector vector = new Vector();
vector.add(new Object());
Object object = (Object)vector.get(0);
Java always passes references by value. So whenever you use a reference as an argument to a function call, the reference value is copied. The object itself is not passed, a copy of its reference is. Its an important distinction to understand. It also is important to understand that with the reference you (or the library) can still operate on the object passed via its reference.
Your snippets are not entirely the same. In (1) you end up with two references to the same object, objectRef and object. In (2) you end up with only 1, object. In both cases the vector has a different reference to the object.
Both snippets are the same, the only difference is that you have a location variable named objectRef which can be modified after it was added to the vector, if it is modified, it will be reflected in the object returned from the vector as well since it IS the same object. Though the "Object" class doesn't exactly have any methods which can modify the object.
That's correct. In the java programming language there is only heap. Every object exists out there in magic heap land. Every non-primitive value is just a pointer whose only operation is to dereference. A List can be thought of as a list of pointers to strings, the actual data content of the strings is out on the heap, not inside the collection structure.
(This is the semantics of the language of course. Modern runtimes are under no obligation to actually do it that way, the JIT uses method stacks, it just has to behave exactly the same as if it worked that way.)
They result in the same state except that at the end of snippet 2, you don't have a symbol called objectRef.
Both snippets give the same results. The difference lies that in the first snippet you have three references to the same object (objectRef, object and a reference in vector), and in the second snippet you only have two references to the same object (object and a reference in vector).