Pass by reference or value?

G

getsanjay.sharma

Hello friends, I am facing a lot of confusion over a simple issue of
parameter passing. Just let me know what I have figured out is right
or wrong:

"There is no pass by reference in Java. Everything is passed by value.
In case of primitive types, a copy of the variable which holds its
value is made and passed to the called function. In case of objects, a
copy of the reference is made and passed to the called function. It is
this reference variable which holds the actual reference to an object.
Think of the reference variable as a container which holds a remote
control, the remote being the object reference. When a reference
variable is passed, this remote is passed by value hence the called
function can manipulate the passed object. An exception here is the
objects of class String since Strings in Java are immutable."

Looks good? Any interesting links would be appreciated.
 
E

Eric Sosman

Hello friends, I am facing a lot of confusion over a simple issue of
parameter passing. Just let me know what I have figured out is right
or wrong:

"There is no pass by reference in Java. Everything is passed by value.
In case of primitive types, a copy of the variable which holds its
value is made and passed to the called function. In case of objects, a
copy of the reference is made and passed to the called function. It is
this reference variable which holds the actual reference to an object.
Think of the reference variable as a container which holds a remote
control, the remote being the object reference. When a reference
variable is passed, this remote is passed by value hence the called
function can manipulate the passed object. An exception here is the
objects of class String since Strings in Java are immutable."

Looks good? Any interesting links would be appreciated.

Partly sound, partly skewed.

You're right about argument passing: Java passes method
and constructor arguments by value, period. Some arguments
are primitive values and some are reference values; *none*
are objects. If you are careful to distinguish references
from objects, your quoted paragraph can be greatly simplified.

As for manipulating the objects whose references are passed:
The method or constructor can *always* manipulate any object it
has a reference to, understanding that "manipulate" need not
imply "modify." There's no need to make special exceptions for
String or other so-called immutable classes; calling str.length()
or str.hashCode() is just as much a "manipulation" as calling
any other method. (Indeed, hashCode() changes the internal state
of a String object the first time it's called on that object: by
computing and caching the hash code!) Immutability (to the extent
it exists at all) has no interaction with argument passing.
 
R

Richard Reynolds

Hello friends, I am facing a lot of confusion over a simple issue of
parameter passing. Just let me know what I have figured out is right
or wrong:

"There is no pass by reference in Java. Everything is passed by value.
In case of primitive types, a copy of the variable which holds its
value is made and passed to the called function. In case of objects, a
copy of the reference is made and passed to the called function. It is
this reference variable which holds the actual reference to an object.
Think of the reference variable as a container which holds a remote
control, the remote being the object reference. When a reference
variable is passed, this remote is passed by value hence the called
function can manipulate the passed object. An exception here is the
objects of class String since Strings in Java are immutable."

Looks good? Any interesting links would be appreciated.
Pretty much, you can't write a swap function in java.
There are other immutable classes as well as String, plus you could write
your own of course.

The example I like to use to explain parameter passing is to pass a mutable
Object, x, to a method, then in the method do x = new Whatever() and then
show that x hasn't changed back in the calling method, but if I do
x.setSomeValue(...) in the method show that the effect is seen outside.
 
M

Mark Rafn

"There is no pass by reference in Java. Everything is passed by value.

Technically true. But confusing if you don't realize that object variables
are already references, so passing them by value has the same effect as
passing by reference in some other languages.

So you're passing a reference by value. How's that for confusing?
In case of primitive types, a copy of the variable which holds its
value is made and passed to the called function.

Variables aren't copied. Values are copied. The variable is 'x'. There's
no 'x' passed to the method. The value is 7. That's copied and passed to the
method.
In case of objects, a copy of the reference is made and passed to the
called function.

Right. The value of the variable (the reference) is copied and passed to the
method.
It is this reference variable which holds the actual reference to an object.

Remove the word variable from that sentence. There's a reference to the
object. It is assigned to a variable. The variable is said to be a reference
to the object, in the same way as an int variable is said to be 7. But the
variable and the value are different things.

The reference is copied, put on the stack, and passed to the method. In
exactly the same way as the 7 is copied, put on the stack, and passed to the
method.

Stated another way, a new reference to the object is created and put on the
stack.
An exception here is the objects of class String since Strings in Java
are immutable."

There's no exception for String, or for Integer, or for any other
immutable object. The reference is copied and passed.
 
M

Mike Schilling

Hello friends, I am facing a lot of confusion over a simple issue of
parameter passing. Just let me know what I have figured out is right
or wrong:

"There is no pass by reference in Java. Everything is passed by value.
In case of primitive types, a copy of the variable which holds its
value is made and passed to the called function. In case of objects, a
copy of the reference is made and passed to the called function. It is
this reference variable which holds the actual reference to an object.

Up to here, you're perfect.
Think of the reference variable as a container which holds a remote
control, the remote being the object reference. When a reference
variable is passed, this remote is passed by value hence the called
function can manipulate the passed object.

I think "container" is misleading, but not really incorrect. Perhaps you
mean "container" in that it can hold different reference values? Yeah,
that's OK.
An exception here is the
objects of class String since Strings in Java are immutable."

There are no exceptions. Strings being immutable merely limits what you can
do via the remote control. You can't change them, but you can interrogate
them in all sorts of ways.
 
S

sakcee

Hello friends, I am facing a lot of confusion over a simple issue of
parameter passing. Just let me know what I have figured out is right
or wrong:

"There is no pass by reference in Java. Everything is passed by value.
In case of primitive types, a copy of the variable which holds its
value is made and passed to the called function. In case of objects, a
copy of the reference is made and passed to the called function. It is
this reference variable which holds the actual reference to an object.
Think of the reference variable as a container which holds a remote
control, the remote being the object reference. When a reference
variable is passed, this remote is passed by value hence the called
function can manipulate the passed object. An exception here is the
objects of class String since Strings in Java are immutable."

Looks good? Any interesting links would be appreciated.

In almost all programming languages(I think), call to a
method(function) results in a
context pushed to stack. all the variables are passed as copies ,
hence by value.
if the thing passed in a Java Referance, its copy inside the stack
context will
still be the same reference.
same logic applies to C's pointer, referance, etc
 
L

Lew

In almost all programming languages(I think), call to a
method(function) results in a
context pushed to stack. all the variables are passed as copies ,
hence by value.
if the thing passed in a Java Referance, its copy inside the stack
context will
still be the same reference.
same logic applies to C's pointer, referance, etc

I don't know about "almost" all, but a few major programming languages (C++,
FORTRAN, to name two) support pass-by-reference semantics. If you weight the
language by their significance the "almost" is canceled.

They don't copy the contents of the variable in such cases but the address.
These languages don't necessarily distinguish variables from references with
the rigor that Java does.
 
G

getsanjay.sharma

As for manipulating the objects whose references are passed:
The method or constructor can *always* manipulate any object it
has a reference to, understanding that "manipulate" need not
imply "modify." There's no need to make special exceptions for
String or other so-called immutable classes; calling str.length()
or str.hashCode() is just as much a "manipulation" as calling
any other method. (Indeed, hashCode() changes the internal state
of a String object the first time it's called on that object: by
computing and caching the hash code!)

How does and in what context is "manipulation" different from
"modification"? Or is it that the functions called on the immutable
object lend to its "manipulation"?

Pretty much, you can't write a swap function in java.
There are other immutable classes as well as String, plus you could write
your own of course.

Sorry for taking this off topic, but how would you make a custom class
immutable?

The reference is copied, put on the stack, and passed to the method. In
exactly the same way as the 7 is copied, put on the stack, and passed to the
method.

Stated another way, a new reference to the object is created and put on the
stack.

Hmm..any links which can explain this very mechanism in-depth with
respect to programming languages esp Java.

I think "container" is misleading, but not really incorrect. Perhaps you
mean "container" in that it can hold different reference values? Yeah,
that's OK.

I heard that term on some site explaining variables. There it was said
that "consider variables to be like a cup which can hold different
values in different situations". Still thanks for the correction.
 
M

Mike Schilling

Lew said:
I don't know about "almost" all, but a few major programming languages
(C++, FORTRAN, to name two) support pass-by-reference semantics. If you
weight the language by their significance the "almost" is canceled.

They don't copy the contents of the variable in such cases but the
address. These languages don't necessarily distinguish variables from
references with the rigor that Java does.

C++ allows both "passing pointers by value" like Java and "passing by
reference". The semantics of both are precisely defined. One thing I would
not accuse C++ of is "lack of rigor".
 
P

Patricia Shanahan

Sorry for taking this off topic, but how would you make a custom class
immutable?
....

Write a class with the following properties:

1. All fields are private.

2. Only the constructors modify fields.

3. A constructor only modifies fields in the object it is constructing,
not in any other instance of the class.

Instances can still be modified by reflection-abuse, but for all normal
purposes they are immutable.

Patricia
 
C

Chris Smith

Patricia Shanahan said:
...

Write a class with the following properties:

1. All fields are private.

2. Only the constructors modify fields.

3. A constructor only modifies fields in the object it is constructing,
not in any other instance of the class.

Instances can still be modified by reflection-abuse, but for all normal
purposes they are immutable.

I'd add:

4. Make either the class, or all of its methods, final.
 
P

Patricia Shanahan

Chris said:
I'd add:

4. Make either the class, or all of its methods, final.

Good point. Without that, a subclass could effectively change a field,
by overriding each method that uses it to use something else.

Patricia
 
L

Lew

in message
Mike said:
C++ allows both "passing pointers by value" like Java and "passing by
reference". The semantics of both are precisely defined. One thing I would
not accuse C++ of is "lack of rigor".

You're right, "rigor" isn't exactly the concept I'm going for. "Rabidity",
perhaps?

In any event, I didn't mean to imply lack of precision in C++ or FORTRAN, only
the presence in Javamind of a very firm distinction not so prevalent in the
mindsets of those venerable ancestors.
 
E

Eric Sosman

How does and in what context is "manipulation" different from
"modification"? Or is it that the functions called on the immutable
object lend to its "manipulation"?

"Immutable" is a fuzzily-defined concept. For example, it
is common to say that String is immutable, even though some of
its internal state can change after the String has been created
(as by hashCode, for example).

One might say that the object is still "immutable" if the
changes to its internal state are not "visible" outside the
object itself. In the case of hashCode, one might argue that
there is no way for the caller to detect whether the returned
value was freshly-computed or was cached. And yet, there might
in fact be a way to do so: If you made very careful timings of
hashCode on a very long string, you might be able to observe
that the first call took longer than subsequent calls; does
this amount to a difference in behavior?

For that matter, it is in fact possible to "change" an
existing String object in such a way that, say, charAt(0)
returns different values at different times. (You use what
Patricia Shanahan calls "reflection abuse" to find the char[]
array underlying the String, and then you change the values
of the array elements.) So it turns out that that String is
only immutable in the face of "normal" operations -- which
really says only that String cannot be changed unless you
change it! By that definition, *every* class is "immutable:"
just label any value-changing operations as "abnormal."

But let's go ahead and restrict ourselves to "normal"
operations. Can we get visible changes in behavior from
our immutable Strings?

// synchronized ("string")
{
Thread t = new Thread(new Runnable() {
public void run() {
synchronized ("string") {
System.out.println("in thread");
}
}
});
t.start();
System.out.println("thread started");
t.join();
System.out.println("thread finished");
}

Clearly, the code's visible behavior -- its output -- depends
on whether the first line is or isn't commented out. What is
the difference? In one case the second thread can run to
completion, and in the other it cannot. What is the reason for
this difference? It has to do with whether the String "string"
is or isn't locked -- that is, it has to do with the state of
the supposedly immutable object "string". A change in the state
of "string" produces a change in the behavior of the program; how
can we keep straight faces while we talk about this state change
and still say "immutable?"

Immutability is a useful concept, but hard to pin down with
exactitude. "I know it when I see it," as Justice Potter Stewart
said of another notion; the fact that he could do no better is
evidence for the existence of things that seem easy to understand
but prove hard to define. I believe "immutability" is one such.
 
G

getsanjay.sharma

// synchronized ("string")
{
Thread t = new Thread(new Runnable() {
public void run() {
synchronized ("string") {
System.out.println("in thread");
}
}
});
t.start();
System.out.println("thread started");
t.join();
System.out.println("thread finished");
}

Thanks to Eric and the others for their enlightening advice. What I
don't understand here is why removing the commented out first line
makes the program go in loop? Why is it not the case with the second
synchronized block?

Sorry for asking simple questions.

Regards,
STS.
 
J

Jim Korman

Thanks to Eric and the others for their enlightening advice. What I
don't understand here is why removing the commented out first line
makes the program go in loop? Why is it not the case with the second
synchronized block?

Sorry for asking simple questions.

Regards,
STS.

The outer Thread running main is holding a lock on the object "string"

It then starts the runnable which attemps to gain a lock on the same
object "string". Remember that in this case "string" has been
"intern"ed so all "string" references are the same object!

The code isn't "looping", its deadlocked waiting for a resource that
can not be released.

Jim
 
M

Mike Schilling

Jim Korman said:
The outer Thread running main is holding a lock on the object "string"

It then starts the runnable which attemps to gain a lock on the same
object "string". Remember that in this case "string" has been
"intern"ed so all "string" references are the same object!

The code isn't "looping", its deadlocked waiting for a resource that
can not be released.

It's a subtle point that the two occurences of the constant "string" refer
to the same object.
 
G

getsanjay.sharma

Thanks a lot Mike and Jim for your explanation. It had slipped my mind
that each object has a implicit lock which one must acquire to enter a
synchronized block.

How would I use 'reflection abuse' to change the data inside a string.
I tried using it but it gave me a 'security exception' saying that I
can't modify the private field. I thought it was possible using
reflection to do that. Any suggestions?

Thanks and regards,
S T S
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

No members online now.

Forum statistics

Threads
473,995
Messages
2,570,230
Members
46,819
Latest member
masterdaster

Latest Threads

Top