24 ms·
Java is Pass-by-Value, Dammit
- Osiris 12y agoI work full-time in JavaScript and I've always thought of JavaScript as a pass-by-reference but this article made it clear that JavaScript is pass-reference-by-value. The `swap` function from the article doesn't swap the variables outside of the function.
- jacquesm 12y agojavaScript != java...
- rcconf 12y agoThe behaviour of JavaScript is equivalent for references. (Call by sharing)
- Osiris 12y agoYes, but the way function parameters are passed is the same. I wrote the swap function in JavaScript and it behaves exactly like the Java version, as opposed to the true "pass by reference" examples.
- miralabs 12y agoIn short: Java has pointers and is strictly pass-by-value. It's a well know fact that Java has pointers given that you have NullPointerException as an exception.
- deleted 12y ago[deleted]
- xaa 12y agoCorrect me if I'm wrong (my Java's rusty), but isn't the most common NPE scenario when a class has a member variable that's a class and has to be initialized in the ctor or elsewhere, but the programmer forgets to. The alternative to this seems to be to require every class to have a no-arg ctor in order to be a member variable of another class. C++ takes this route, and it has the irritating effect of making iostreams, for example, hard to work with.
- Jweb_Guru 12y agoThe best way to deal with this by a substantial margin is to simply not have uninitialized variables, ever, which means you don't need null in the first place (you can replace the functionality with optionals if you really want to, but usually it's not necessary). When I write Java, I declare fields final wherever possible for this and other reasons.
- jtheory 12y agoFinal is a useful keyword -- a way to make the compiler flag up risky code. :) The problem (the rest of the time), though, is that if you're writing object-oriented code, some values are simply null. Some data points are unknown, or some properties won't have values for some instances. If you create an new object but it hasn't been persisted yet, it has a null ID. If you're working with Categories (of something), some may have a parentCategory and some may not (null). You can set a placeholder of some kind -- e.g., "-1" means no ID, NO_PARENT is a special Category to return from getParentCategory() if there's no parent, etc.. But then you still need extra code to handle these not-actually-valid values, and when your code is bad, instead of fast-failing with a NullPointerException... things will work, but weirdly. You'll get more confusing errors, further away from the actual bad code. The Apache Commons way to deal with null is something of a hack, but it works -- library methods for common actions with built-in null handling. E.g., StringUtils.isBlank(s) is true if s is null, or empty, or only whitespace. ObjectUtils.isEquals(o1, o2) is true if both are null, false if only one is null, or true if o1.equals(o2). CollectionUtils.isEmpty(c) returns true if the collection is null, or empty. I haven't much explored other OO-based approaches to null that are less annoying than Java's handling -- so I'm always curious to hear about smarter approaches.
- peeters 12y agoOP mentioned one of the other approaches..."Optional". An `Optional<String>` will be a non-null reference to either a present value, or an absent value. It's really just modelling null at a non-syntax level, and encourages checking whether there is a value explicitly (i.e. it's self documenting that you need to check if the value is present before using it). Proponents of Optional will then say that every non-Optional reference must never be null, through static/runtime assertions (like @Nonnull, checkNotNull(), etc)
- uiri 12y agoThe confusion around whether or not Java has pointers comes from people comparing it with C or C++. In Java, you can't dereference a pointer to an Object and get some sort of Object value. Similarly, you can't perform an "address of" operation on a primitive value and get a pointer to that value. Similarly, you can't pass-by-reference (in the sense of the parent article) or do pointer arithmetic in Java. While Java technically has pointers (in the sense that it has pointer types), it has dulled them so that you can't hurt yourself with them the same way that C (and C++) permit.
- moogly 12y agoFWIW, in .NET land, we tend to say "pass-by-reference-by-value".
- MaxGabriel 12y agoI call this "pass by pointer copy". Does anyone know if that's a term people use, or did I just invent it? I can only find one other person mentioning it when I google for "pass by pointer copy" (in quotation marks for the exact match).
- jeff_marshall 12y agoNo,that's completely natural (if verbose). This is from someone coming from a C background, FWIW.
- coldtea 12y agoShouldn't it be: pass-reference-by-value
- lucio 12y ago>Java is strictly pass-by-value, exactly as in C In C you can pass a pointer, and a pointer to a pointer. I understand both cases are usually called "pass-by-reference". If you call "pass-by-value" to passing a pointer, then the notion of "pass-by-value" and "pass-by-reference" are not very useful. IMHO "pass-by-reference" means you can mutate the attributes of the thing passed (as in java when you pass an object) and also means you can be operating on a "volatile" area of memory, meaning another thread can CHANGE the data while the function is executing. OTOH "pass-by-value" means you get a "snapshot" of the value at the point of the function-call, the copy is normally on the stack, and no other thread will change the data while the function is running. Also you can mutate the area with gusto without worrying of data-races, side-effects or altering the calling function variables. This two "definitions" of pass-by-value and pass-by-reference are the ones I find useful regarding concurrency and side-effects. If you tell me that passing an integer and passing an object are both the same thing (pass-by-value) in Java, then I will tell you that pass-by-value and pass-by-reference are not very useful concepts.
- argonaut 12y agoIt is a useful concept because there are languages with pass-by-reference constructs. C++, Swift (sort of, with inout parameters), are two examples that come to mind. Java and C are simply not those languages.
- cube00 12y agoYou can pass double pointers in C so functions can change the original pointer's address value. You can't do that in Java.
- ta82828 12y agoYes, you can do that in C, but that is still not pass by reference. In C you are not passing the variable you are trying to change, you are passing a pointer to it. You cannot write swap(a, b); You have to write swap(&a, &b);
- TazeTSchnitzel 12y agoPHP unfortunately has the same issue because it copied Java's terminology to describe object reference values (introduced in PHP 5), yet it has always also had "references" which are actually pass-by-reference. To demonstrate, object references/pointers/whatever: $foo = new Foo(); // $foo $foo2 = $foo; $foo2->x = 3; // $foo->x is also 3 now, $foo and $foo2 point to the same Foo object // that is, $foo and $foo2 both contain an object handle/pointer/reference/whatever that points to the same Foo object PHP references: function swap(&$a, &$b) { $temp = $a; $a = $b; $b = $temp; } $a = 3; $b = 2; swap($a, $b); // $a is now 2, $b is now 3
- deleted 12y ago[deleted]
- Terr_ 12y agoThe only reason I use @-refs anymore is because of PHP copying arrays on assignment (shallowly, lazily.) In addition--unless you do everything in a super-functional way--you need to unset() each &-ref to prevent latent bugs later in the same scope. It's an unfortunate situation, and it gets worse when you add array-like-objects into the mix, which look exactly like "normal" arrays up until the moment everything explodes into WTFs.
- judk 12y agoThe terms are not precisely enough to give meaning to cross-language comparisons. Within a single language like C++, you can usefully differentiate the various ways to pass references and data.
- ta82828 12y agoI disagree. The question of whether or not you can write a swap function as described in the article is fairly precise.
- deleted 12y ago[deleted]
- deleted 12y ago[deleted]
- ta82828 12y agoI don't see how the article you linked to contradicts the original post.
- TazeTSchnitzel 12y agoThe author doesn't seem to understand how parameters work.
- jackmaney 12y agoNo, the Java language specification makes it as clear cut as anything can get.
- deleted 12y ago[deleted]
- nickbauman 12y agoWell the way I've always thought of it is that Java passes "references by value". Meaning the target method receives a _copy_ of the pointer, not the actual pointer. So the result of newing up the parameter inside the target method doesn't affect the original, because you're just making the pointer point to a NEW memory address. On the other hand, mutating the parameter WILL affect the original object, because a copy of a pointer still points to that object from the caller.
- cbd1984 12y ago> Java passes "references by value". Meaning the target method receives a _copy_ of the pointer, not the actual pointer. Which is exactly how C does it. I don't see how this is a difficult enough concept to grasp that we need an article explicitly pointing out how Java is just like C in this respect.
- Dylan16807 12y agoBecause in C you have to specifically ask for something to be a pointer. "pass by reference" is an incorrect phrasing, but at least it's an attempt. There is a crucial distinction between Java and C. And C++ shows actual reference passing.
- cbd1984 12y ago> "pass by reference" is an incorrect phrasing No, it isn't. In C, a pointer is a reference. It supports arithmetic, but it works like a reference as well, so the name applies. What might confuse people is that in C, you do have to specifically ask for a reference to something, whereas in Java, everything which isn't a primitive type is already a reference. It's true your code can't dereference those references such that it gets access to all of the data in a List object, for example. C works the same way, again: It's entirely possible to say something like 'typedef struct foo mfoo;' and then declare all of your functions to take pointers to type mfoo, and client code will never be able to get its hands on a struct foo object. FILE pointers work just like this, for example.
- lucio 12y agoThis topic (I do not know why) raises some serious emotion-based responses on coders. The other topic I know will cause almost a religious flame-war is the philosophical meaning of "null" in the SQL arena. I've tried to add some insight why the OP hears (so many) >folks (incorrectly) state "primitives are passed by value, objects are passed by reference" What I believe was my constructive addition to the topic, seems to deserve only downvotes. I'll make a reminder to not participate again in this kind of topics.
- ubernostrum 12y agoCould be worse: could be one of the debates about Python, where people who don't work in Python insist that it must follow one or the other paradigm (when trying to shoehorn either a consistent pass-by-value or a consistent pass-by-reference interpretation on Python's behavior will lead you to write code with bugs).
- Veedrac 12y agoHow is Python not pass-pointer-by-value?
- ubernostrum 12y agoThe main issue, as I noted, is people who come from other languages and have preconceived notions about what "pass by value" and "pass by reference" mean and preconceived expectations about language behavior as a result. In Python, worrying about whether it's "pass-by-X" paradigm is practically worthless; instead, what you want to know in Python is which types are mutable.
- flomo 12y ago> This topic (I do not know why) raises some serious emotion-based responses on coders. I saw the title on HN, and was like "uhhh, no shit, why is this here?". Then surprisingly, it all of a sudden it has 80 points and almost 50 comments debating the details. I don't think there's any actually real debate on how Java actually works, this must be a purely linguistic. Or as you say, "emotional". SQL NULLs, on the other hand, is a real philosophical war. One which the wrong size is clearly wrong and need to be crushed into ashes underneath our boots. We are not debating jargon, we are defining databases which could certainly outlive our sons and daughters!!!! .. Ok, sorry. But I just don't think it's good comparison with students who just don't really get Java. Database design is largely a matter of opinion, Java method calls are not.
- rspeer 12y agoDear author: webhostinggeeks did not actually translate your article into Serbo-Croatian for free. They just ran a shitty automatic translation and added in links that boost their black hat SEO empire. They target many people who host highly linked articles this way. They picked Serbo-Croatian because you're unlikely to verify it. Do not post translations unless you trust the translator (perhaps because you paid them to do good work) or know the language.
- viraptor 12y agoI gave up on this... It's explicitly said in the Java standard that the language is pass-by-value. On one occasion I've been told that the standard must be wrong then. Some people just don't want to accept reality if it doesn't match their interpretation of definitions. :-(
- kremlin 12y agoCalling it "pass by value" without qualifying that, for objects, it passes the reference by value, is very confusing.
- viraptor 12y agoBut these are completely separate things. You can have any mix of those (c# actually has all): - Pass by value, values hold object references. (java, c# objects) - Pass by value, values hold objects. (c# structs) - Pass by reference, values hold object references. (c# inout parameter, passing object) - Pass by reference, values hold objects. (c# inout parameter, passing struct)
- agricola 12y agoI'm not really sure what point you are trying to make here. In general, the whole thing about passing a reference by value is just BS. What you need to ask is, "What am I passing to the function?" If you are passing an object, and Java (or whatever language you are using) determines a reference (memory address or whatever), then passes that reference to the function, then you are, by definition, passing an object by reference. The important thing to focus on in this argument is, "What am I passing?" The answer for this scenario is that the programmer is trying to pass the object itself. Who cares about the address / location of the object. If you decide to pass the reference explicitly, then you are passing a reference, not the object. This would be like explicitly passing a pointer in c++, and is apparently a controversial topic when it comes to Java. A reference will nearly always (I can't actually think of a case where it isn't) be a primitive, and therefore, be passed by value. For argument sake, say I'm wrong about all this. My question would be, "What would it look like to pass an object by reference, and how does that differ from what is currently happening?"
- furyofantares 12y agoThe confused terminology isn't related to function calls. In Java, objects are not values. The confused terminology originates before you get to function calls -- you can't ask "are objects passed by value?" without first considering objects as values. Objects can't be stored in variables and objects cannot be the result of an expression. x = y does not copy an object y into an object x because objects are not values -- x and y are variables and they can only hold values, which objects are not.
- zvrba 12y agoOf course it is. It says so in the language spec, and even in the official tutorial here: http://docs.oracle.com/javase/tutorial/java/javaOO/arguments.html http://docs.oracle.com/javase/tutorial/java/javaOO/arguments... Swap is a nice litmus test. To people who claim that Java doesn't have pointers, I counter-argument by the fact that you can make a circular doubly-linked list in Java. Thus, a reference is a pointer though with lesser capabilities than in C++. In contrast, you cannot make a circular doubly-linked list with C++ references which are object aliases. Actually, I have the following analogy: pointer ~ symbolic link; reference ~ hard link. Java's references are misnamed.
- tomjakubowski 12y ago> Java's references are misnamed. That's silly. Why should every other language adhere exactly to C++'s definition of a reference? 'Reference' as a concept exists outside of computer programming and Java isn't wrong to repurpose the term in a different way than C++. Consider also that C++ has 'dependent types', despite pretty much no relationship to the more well-known definition of dependent types. There are only so many ways to name something.
- evincarofautumn 12y agoThere are also two uses of “dependent” in C++: the resolution of a name can depend on a type parameter, so you have to specify whether you want to treat it as a type name; and a type can depend on (compile-time) values. The former has nothing to do with dependent typing, but the latter does!
- zvrba 12y ago> That's silly. Why should every other language adhere exactly to C++'s definition of a reference? It would be silly if NullPointerException were named something else.
- evincarofautumn 12y agoHere’s an awesome thing: you actually can make a cyclic doubly linked list in C++ with references, in a manner defined by the standard! #include <iostream> struct node { node(node& previous, node& next, int value) : previous(previous), next(next), value(value) {} node& previous; node& next; int value; }; int main(int argc, char** argv) { char buffer[2 * sizeof(node)]; node* a = reinterpret_cast<node*>(buffer); node* b = a + 1; node nil(nil, nil, 0); new(a) node(nil, nil, 0); new(b) node(nil, nil, 0); new(a) node(*b, *b, 1); new(b) node(*a, *a, 2); std::cout << a->next.next.next.value << '\n'; } §3.8¶4 says: “A program may end the lifetime of any object by reusing the storage which the object occupies or by explicitly calling the destructor for an object of a class type with a non-trivial destructor.” We don’t need to call the destructor because we have a POD type and we don’t depend on the side effects of the destructor—there aren’t any—so we can simply reinitialise the objects. However, we have to bootstrap these with valid objects in the first place, because we have to be able to dereference “b” and “a” in order to construct the references.
- carsongross 12y agoJava hides the pointer, which is what confuses people. Maybe we shouldn't be shitty about that, since it doesn't really matter too much. Just a thought.
- Timono 12y agoJava is Pass-By-Value for values and Pass-By-Copy-Reference for objects.
- anon4 12y agoYou absolutely CAN write swap in Java: void <T> swap(T a, T b) { // use the Unsafe to copy a's memory to a temp buffer // then copy b's memory to a // then copy a's memory to b // Caution: Don't pass Integers or anything, okay } Or, if the objects are Beans, just iterate the properties and swap them one by one. In fact, if you know you're dealing with beans, the two don't even have to be the same class, as long as their properties and types are the same.
- bad_user 12y agoNot by using that signature, no you can't.
- shiro 12y agoNo, it's not the same. X a = new X("foo"); X b = new X("bar"); X c = a; swap(a, b); // after this, a points to X("bar") and b points to // X("foo"), but c should remain pointing to X("foo"). If you swap the contents of the object, c would point to X("bar").
- banachtarski 12y agoThe C++ implementation of swap given is wrong. SomeType temp = arg1; This would do a deep copy of the object pointed to by the ref arg1. What is intended is probably SomeType& temp = arg1;
- jjnoakes 12y agoNo, the article was right. You can't do a generic swap without 3 deep copies. If you change temp to be a reference, then once you do "arg1 = arg2", you just lost any way to get arg1's value back.
- DonHopkins 12y agoFrom: James Gosling Date: 1/13/11 Don Hopkins wrote: >Hey I know it's 2011 and we're living in the future and all that, but >there still seems to be some confusion and debate about a matter I >thought was perfectly clear: Is Java pass by value or pass by >reference? Depends on your terminology. But it's kinda both. It's pass-by-value for everything, with the twist that for class instances, the thing that's passed-by-value is the pointer to the object, so it behaves like pass-by-reference. From: Don Hopkins Date: 1/13/11 Reminds me of the controversy about Niklaus Wirth's name: "Whereas Europeans generally pronounce his name the right way ('Nick-louse Veert'), Americans invariably mangle it into 'Nickel's Worth.' This is to say that Europeans call him by name, but Americans call him by value." - Introduction by Adriaan van Wijngaarden at the IFIP Congress (1965). It seems to be a consequence of pretending pointers don't exist -- you also have to pretend you have variables with object values and references, but you still can't write a swap(a, b) function. If you think of Java object values as pointers, then it's obviously passing references by value. But if you don't believe in pointers and think of variables as containing objects, then it's obviously passing objects by reference, but your view of the world is an illusion, because it's really implemented with pointers. Or is it??? Someone suggested a Magic Elves theory, which helps a lot of other stuff to make more sense. Here's the discussion from 2011 about this issue that prompted me to ask James Gosling for a clarification. You can see that many people were VERY confused, and extremely fanatical about maintaining and spreading their confusion, in spite of the fact that it directly contradicted the Java spec and the inventor of Java himself. Java is PASS BY VALUE. http://www.theserverside.com/discussions/thread.tss?thread_id=61622 http://www.theserverside.com/discussions/thread.tss?thread_i...
- lucio 12y agoThe man says: >But it's kinda both. It's pass-by-value for everything, with the twist that for class instances, the thing that's passed-by-value is the pointer to the object, so it behaves like pass-by-reference. So he's saying: We call them all "chickens", but some of them walk like a duck and quack like a duck, so they're basically ducks. You can't extract from that quote "THEY ARE CHICKENS" (all in caps) When he says "kinda both" and "it behaves like pass-by-reference" I read some "subtle" hints saying that he thinks that basically class instances are passed-by-reference.
- moru0011 12y agoif you want pass a reference to a reference do Dog dog[] = { new Dog }; void method( Dog dog[] ) { dog[0] = new Dog(); } Having this of side effect as a default would be an insane idea ofc., so I am not sure what you are complaining about :-)
- DonHopkins 12y agoNo, that's passing by value a reference to an object (Dog array) that contains a reference to another object (Dog). The variable "dog" that is the parameter to "method" is passed by VALUE, not by reference. Passing something by reference is NOT the same as passing a reference to something by value.
- twic 12y agoI remember this being a hot topic on usenet back in the '90s. It's great to see it getting an outing today, and inciting equally as vigorous argument!
- jtheory 12y agoIs there any useful argument to be had around this, for pragmatic purposes? No one disagrees about what Java is doing here (that I know of). Naming is a problem if people are writing bugs due to the poor explanation. But I can't think of the last time I've actually seen bugs caused because anyone who thought that, for example, a swap() method would work in Java. It's something that brand-new developers might muddle up, but usually they'll learn how it works within the first year, no? If they keep track of how to treat primitives vs. objects in methods by saying "Java passes primitives by value, Objects by reference", and that works for them, that's okay. I think a senior dev should know a bit more about what's really going on, but I'm not waste the time of a mid-level programmer because, even though this code is correct, I want to talk for 20 minutes about the reason why it's correct wasn't worded quite right. I'm far more likely to see bugs caused by people misunderstanding Java's auto-boxing/unboxing of primitives for method calls ("how the devil is this line throwing a NullPointerException?").
- knappador 12y agoNovice Java programmer reads title, mutates Java object inside function, later notices side-effects, and curses author of the title. Second novice Java programmer reads title, wants to pass objects into functions, wants to avoid expensive stack copy and writes &myObject, gets compiler error, Googles "Java pointer," and curses author of the title. Lesson learned: author of title is either unaware of the consequences such an interpretation will cause or seeks cursing as a source of attention.
- learc83 12y agoNovice Java programmer doesn't read title attempts to assign a new object to a variable inside a function, doesn't work, curses Java tutorial that said objects are pass by reference.
- knappador 12y agoWhen in C, Python, Java, JS, or anything else does reassigning a variable from the function sig ever work? The symbol is in-scope. Even when overwriting the pointer location in C, you don't just assign; you de-reference and copy over the memory that was there. A novice programmer would make this mistake, not a novice Java programmer.
- mml 12y agoThis entire thread makes me want to die. Please, do not speak of this again.
- jjnoakes 12y agoTop notch contribution.
- AnthonyMouse 12y agoSo to summarize, you have a Java function: public void f(Foo bar) { ... } Which is the equivalent C++ function? void f(Foo bar) { ... } void f(Foo& bar) { ... } void f(Foo* bar) { ... } It's the last one. Java passes everything by value, but non-primitive objects in Java are actually pointers (which Java inaccurately calls references), and the pointer is passed by value.
- goalieca 12y agoThis! People say java passes by reference sometimes, but in C++ the references can't be null whereas in java they can.
- theyoungestgun 12y agoCpp and c also call things volatile for entirely different reasons than Java. These are two distinct ecosystems. They use the same terminology with different meaning. That perhaps is confusing, but definitely doesn't make one or the other incorrect.
- Tobani 12y agoI think this is the big thing. Maybe java references arent cpp refs. Is there a proper name for an abstract construct that refers to something else? Maybe reference?
- wspeirs 12y agoWhy is it inaccurate to call it a reference in Java? You don't dereference a variable in Java to access it, so that would make me think reference, not pointer.
- jjnoakes 12y agoBy you do deference object variables in Java. What do you think the "." operator does?
- diego898 12y agoI asked a question some time ago on SO [1] where Scott Stanchfield - "The Java Dude" weighed in and it sparked quite a discussion. It is well worth reading the discussion there as well as this one. [1] https://stackoverflow.com/questions/934775/changing-value-after-its-placed-in-hashmap-changes-whats-inside-hashmap https://stackoverflow.com/questions/934775/changing-value-af...
- city41 12y agoI had a similar frustration over JavaScript recently and wrote a very similar post: http://www.mattgreer.org/articles/javascript-is-a-pass-by-value-language/ http://www.mattgreer.org/articles/javascript-is-a-pass-by-va...
- JBiserkov 12y agoA pointer in Java Dog d; is exactly like C++'s Dog *d; Following a pointer and calling a method d.setName("Fifi"); is exactly like C++'s d->setName("Fifi");
- solipsism 12y agoYou can absolutely make a swap for reference types in Java. Here: https://gist.github.com/anonymous/d3b4b3bcacb478896ef2 https://gist.github.com/anonymous/d3b4b3bcacb478896ef2 This is analogous to a C++ swap(Type&,Type&). The main difference is that C++ provides a default assignment operator for types, meaning you don't have to provide Assign yourself. A smaller difference is that the temporary instance can be created on the stack in C++ but not in Java. For primitive types it's absolutely true that you cannot implement swap (unless you were to have created that value type in a reference-type wrapper). It's misleading to say you can't do so for reference types.
- jjnoakes 12y agoThis is not the same swap. The article (and the correct pass-by-reference litmus test) swaps the values of the variables as the caller sees them, using operations inside the swap routine. Your example swapped the contents of the pointed-to objects, but did not change the values of the variables a1 and a2. If you want to see the difference, assign a1 to a new variable a3 before the a1/a2 swap call. A real pass by reference swap will end up with a3 == a2, and your example ends up with a3 == a1.
- solipsism 12y agoYes it is the exact same swap. Either behavior (what you call a3 == a2 and a3 == a1) is possible in either C++ or Java, depending on what you mean by "assign a1 to a new variable a3". Your confusion is surely that C++'s assign-by-value looks like Java's assign-by-reference. Again, either behavior is achievable May I invite you to write some code and see for yourself? Here: C++ Swap (what you and the article call the litmus test): https://gist.github.com/anonymous/06b9251a37008d158f59 https://gist.github.com/anonymous/06b9251a37008d158f59 Java Swap (exactly the same thing): https://gist.github.com/anonymous/d57d272579079b4e9ee8 https://gist.github.com/anonymous/d57d272579079b4e9ee8 These programs don't only output the exact same thing, they do exactly the same thing (except the differences I noted above, about the default copy assignment operator being implicit in C++, and about C++ putting the temp variable on the stack instead of the heap).
- deleted 12y ago[deleted]
- jjnoakes 12y agoSorry. But this just is not right. Pass-by-reference has a specific meaning, and by ignoring that, you are adding to the confusion and doing a disservice to everyone who genuinely wants to learn what is right. Stop doing that. If you "x = new Foo()" inside a routine and it changes the value of y in "call(y)" then it is pass-by-reference. Period. Java does not do this. Java is pass-by-value only. Just because you can dereference your copy of a variable holding an object reference (or pointer - they are synonymous in the JLS) and mutate the pointed-to object, which the caller can then see through their copy of their pointer variable, does not mean you are passing by reference. You are passing an object reference (pointer) by value.
- agricola 12y agoI think people are reading way too much into what a reference is. In c++, it has a very specific meaning, but in Java it has a slightly different definition. In c++, the only difference between a reference and a pointer is in the dereference syntax, and that a pointer can be reassigned. In the background, the variable is a pointer in both cases. It is simply syntactic sugar. Another thing some people are mixing up is the entire philosophy between pass-by-reference and pass-by-value. The ability to write a simple swap function does not accurately demonstrate what a language is doing. It is quite simply whether or not the compiler creates a copy of the object (not a copy of the address / pointer / reference). If, in the background, Java passes an address / pointer / reference (the word makes absolutely no difference), when the programmer is attempting to pass an object, that is the definition of pass-by-reference regardless what arbitrary word I want to name the referencing value. Yes, the pointer is a copy of the previous pointer, but that's not the explicit value that the programmer cares about. Yet another comparison to c++: the same thing happens with pass-by-reference in c++. If a function has the prototype: void foo(Dog& d); and I pass a Dog object in a call similar to: Dog d("Spot"); foo(d); then, in the background, it is going create a reference (i.e. the address), and copy it on the stack. In my foo() function, the argument is simply already dereferenced (I don't have to treat it like a pointer). TLDR... If you pass an object to a function, and operations performed by that function affect the original object, it is pass-by-reference. Period.