A flamewar on java dev forums WTF



  • http://forum.java.sun.com/thread.jspa?threadID=208584&start=345&tstart=0

     

    This little WTF is the reason why developers on avg write 15 working lines of code a day, i sure did when i read this for a few hours during work.
     



  • It's also a good example of what happens if you make a wrong statement, and insted of admitting it, try to redefine the rest of the world, so your statement become true


    (I had not time to read it all, so I just did read the first 4 pages, and the last 4). Still funny thou

     



  • I dont know about you guys, but I hate it when someone says I write just X lines of code a day. Not blaming the original poster though. That metric is so absurd as in suggesting that you've exercised your mind just X times a day.

    I like to reply back with something like this - "X lines of code that walks without crutches."

     

     

     

    *Let the flamewar begin*
     



  • I love their complete inability to communicate using English.  They talk themselves in circles without really saying anything, and when that fails they fall back on code to get their point across.  There's an allegory about developers in that somewhere. . .



  • I'm not a java dev. I'm an amateur c# dev. I don't have a CS degree. let me see if I get this straight.

     In c#, you can either do foo(obj) or foo(ref obj). In the former case, whatever 'foo' does to obj will only affect whatever's going on local to foo. In other words, a copy of obj is made in memory, and the reference is sent off to foo. Maybe stored as the value of a variable, I don't know. I would guess that a pass-by-reference system would pass the reference of the new object to foo, and pass-by-value would store the reference in a variable, and then pass the value of that variable to foo. In the latter case, the reference to obj is taken, and that's sent to foo. Because foo has the reference to the original object obj, it can play around with it and affect that actual object.

     
    So, with java, because it's always pass by value, but objects are never passed, is it always the case that when I do foo(obj) that obj is copied, the new reference to that object stored in a variable, and the value of that variable passed to foo?
     



  • The most amusing thing about that "conversation" is that they're basically all arguing the same point, they're trying to convince each other of something they all agree on.

     



  • [quote user="growse"]

    I'm not a java dev. I'm an amateur c# dev. I don't have a CS degree. let me see if I get this straight.

     In c#, you can either do foo(obj) or foo(ref obj). In the former case, whatever 'foo' does to obj will only affect whatever's going on local to foo. In other words, a copy of obj is made in memory, and the reference is sent off to foo. Maybe stored as the value of a variable, I don't know. I would guess that a pass-by-reference system would pass the reference of the new object to foo, and pass-by-value would store the reference in a variable, and then pass the value of that variable to foo. In the latter case, the reference to obj is taken, and that's sent to foo. Because foo has the reference to the original object obj, it can play around with it and affect that actual object.

     
    So, with java, because it's always pass by value, but objects are never passed, is it always the case that when I do foo(obj) that obj is copied, the new reference to that object stored in a variable, and the value of that variable passed to foo?
     

    [/quote]

     

    Java is pretty screwy in places, but thankfully, it's not that screwy. The object references are passed by value. The objects are never duplicated, unless you manually make a bitwise copy. The notion of references being passed by value is picky, but the implication is something like this (I think):

    public class IntHolder {
    	public int myInt;
    	public IntHolder(int pMyInt) {
    		myInt = pMyInt;
    	}
    }
    

    Then elsewhere:

    public static void foo() 
    	myIntHolder = new IntHolder(7);
    	System.out.println(myIntHolder.myInt);
    	bar(myIntHolder);
    	System.out.println(myIntHolder.myInt);
    }
    public static void foo(IntHolder pIntHolder) {
    	pIntHolder.myInt = 8;
    	pIntHolder = new IntHolder(9);
    }

    So running the method foo() will print this output:

    7

    8

    Correct? I haven't done Java in quite some time - thankfully ;-) - but I seem to remember it working like that. 



  • After reading that thread, I find myself rather distressed.  I am worried that somehow I might become subconsciously affected by daFei's distorted, strange non-logic.  It's as if it might be some sort of viral disease, contagious merely by reading his false, perverted arguments.



  • Ok, so the method "bar" (I assume the second "foo" is "bar") takes the object at address 'pIntHolder' and modifies it. Then it writes a new address into 'pIntHolder'. As a result, you've modified the original object at that address, and you get "8" printed, but putting a new address into pIntHolder is irrelevant, because the foo() method doesn't know/care about pIntHolder. However, if it was pass by reference, pIntHolder would contain the original address of the object. Therefore putting a new object there would write a new address into that variable. The old object at the old address would be unreachable?

     I think I'm getting there. When i say Object bleh = new Object(), bleh is a refernce variable which contains the address of the object. This makes sense. Yes. I see.

    Just to be clear, in my above example, 'bleh' is a reference variable which contains an address, that has an address of it's own, which I could store into another reference variable - 'wibble'. This would then contain the address of 'bleh' which would contain the address of the object?
     



  • Also, does this mean that if, in java, I do the following:

     object bleh1 = new object();

    object.property = 3;

    object bleh2 = bleh1;

    bleh2.property = 5;

     
    If I now print out bleh1.property, will it be 3, or 5? If "object bleh2 = bleh1;" just copies the address of the object into bleh2, then by modifying bleh2, I've also modified bleh1, and so I'll get 5. However, if the entire object is copied, then bleh2 is pointing at a completely different address to bleh1, and a completely different object, and I'll get 3.

    Which do I get?

    *edit* woooo, tested on c# - i get 5! never knew that. You learn things every day :)
     



  • [quote user="growse"]Just to be clear, in my above example, 'bleh' is a reference variable which contains an address, that has an address of it's own, which I could store into another reference variable - 'wibble'. This would then contain the address of 'bleh' which would contain the address of the object?[/quote]

    Pretend addresses are plain old integers.  As such, pretend at the binary level, "varA" is converted to an int, and "varB" is converted to an int.  When you execute "varA = new Object()", you are assigning "new Object()'s" integer address to 'varA'.  Let's say that the address is "1".  So under the hood, the following assignment occurs, "varA = 1".

    Make sense so far?

    When you execute "varB = varA", you are assigning varA's integer value to "varB", not varA's own address.  In other words, varB's value is 1. Now, if I execute "varB = 2", varB no longer has the same integer value (address) as varA, but nothing has happened to varA.



  • Sure, I get that - the revelation I had that varA doesn't contain an object which might be 20k long, but the address of that object. If I do varB = varA, then the integer address ("1", say) gets copied to varB, and the integer value of varB now points at the same object as varA. If i start to manupulate the object at varB, varA appears to change. If I assign a new object to varB, a new address is stored as the value of varB, varA doesn't care.



  • I thought everybody knew that objects in Java are passed by pony express.



  • Did I read that correctly?  526 replies?

    And yes, it's just dorks with horrible communication skills bickering over what "reference" and "by value" really mean.  A few people appear to honestly want to know the difference, but they're drowned out by the posturing weenies.

    I don't plan to ever read that thread all the way through, but I would hope that someone just put it to rest by comparing passing an Object to passing a pointer as an argument to a C (not C++) function.



  • Unfortunately it looks like they are still going at it, all because they aren't using the same meaning for the same words, and refuse to notice. Yeah, a C/C++ example would be a good thing. All java variables (other than primitives) hold a pointer, which is passed by value. Arguing whether or not that constitutes passing by reference is a good example of a waste of time.



  • Wow, it took my 2 pages to actually believe it.  The only thing they are arguing about is if the passing of objects in java is pass-by-reference or pass-by-value.  And of course the one group argues that a reference to the object is passed-by-value while the other group argues that the object is passed-by-reference.  Obviously those two statements happen to be EXACTLY the same.

     

    PS. what do you mean it's still going on? the last post was on Jun-27th 



  • Wow, fascinating. All that wasted bandwidth just for something obviously stupid; I can see how bothhsides have a point, something that should have cleared somewhere in the first page. Sigh.

    Anyway, I think an better way to describe how C# works is that when using value objects (such as bool, int, and other primitives as well as user defined types using the struct keyword) well, they are passed by value. When you use reference objects (such as Form, Button, SqlConnection, etc as well as user defined types using the class keyword), you are passing them by reference.

    The ref keyword is used for both value and class objects and has basically the same meaning. Passing a value type by reference, you allow the method to change the value of your object. Passing a reference type by ref, you allow the method to do something in the lines of void foo(ref ClassType ct) { ct = new ClassType(..); }

    Note that strings are immutable reference types.



  • [quote user="db2"]

    public class IntHolder {
    public int myInt;
    public IntHolder(int pMyInt) {
    myInt = pMyInt;
    }
    }

    Then elsewhere:

    public static void foo() 
    myIntHolder = new IntHolder(7);
    System.out.println(myIntHolder.myInt);
    bar(myIntHolder);
    System.out.println(myIntHolder.myInt);
    }
    public static void foo(IntHolder pIntHolder) {
    pIntHolder.myInt = 8;
    pIntHolder = new IntHolder(9);
    }

    So running the method foo() will print this output:

    7

    8

    Correct? I haven't done Java in quite some time - thankfully ;-) - but I seem to remember it working like that. 

    [/quote]

    Correct!

    That is a good example why java uses call-by-reference-value (just another name for passing an objects address by-value instead of the actual reference to the object).

    And yes, the other example by growse shows the "reference"-aspect of it.

     

    object bleh1 = new object();    // bleh1 points at the new object

    bleh1.property = 3;                  // the value of the object that bleh1 points at is changed to 3

    object bleh2 = bleh1;               // bleh2 points at the same address as bleh1

    bleh2.property = 5;                  // the object bleh2 points at is changed. its the same object bleh1 points at. Thus both have the same value '5'

     

    (I  corrected the second line where it said obejct.property instead of bleh1.property.)

    <suck up>At this point I'd like to express that I'm very content that this site is (a) well moderated and (b) has quite an intelligent and mature community. We do not have to suffer from immature kiddies that troll and flame as they like. If you look at a lot of other forums theDailyWTF seems to be a safe haven. I really appreciate to be able to participate in a discussion that is based on actual arguments which themselves can already cause enough heat. :)</suck up>

     

     



  • Hey, I'm only nice because I'm both (a) clueless and (b) aware of that fact :)



  • Allow me to misunderstand and redefine all terms used in your previous post when I say: Java dont uses call-by-value for objects (just another name for passing an objects by-value instead of the actual value of the object). this why the three-wire design of JSP isn't by the J2EE design document PROPER. Just by passing by-value of objects it is! But you must count the client in, otherwise the previous proof isn't proven - at least that is what thet say with the design document (I have read this, if you say not you are incorrect!).

     

    How many posts like those posted by daFoi over there, are posted and moderated to oblivion over here? Any moderator willing to share their experience?

    Or are we in fact so lucky as not to have such moronic posters at all in this forum? I sort of find that inprobable, even though this site is so much more serious in contents, I mean some of the posts here must strike some nerve even in daFoi's mind. OTOH, he probably finds most of the WTF:s prime examples of How It Should Be Done(tm) in the Real World, and the Real WTF in daFoi's mind is always that we don't understand how infinitely clever the code in the WTF is.



  • [quote user="growse"]

    I'm not a java dev. I'm an amateur c# dev. I don't have a CS degree. let me see if I get this straight.

     In c#, you can either do foo(obj) or foo(ref obj). In the former case, whatever 'foo' does to obj will only affect whatever's going on local to foo. In other words, a copy of obj is made in memory, and the reference is sent off to foo. Maybe stored as the value of a variable, I don't know. I would guess that a pass-by-reference system would pass the reference of the new object to foo, and pass-by-value would store the reference in a variable, and then pass the value of that variable to foo. In the latter case, the reference to obj is taken, and that's sent to foo. Because foo has the reference to the original object obj, it can play around with it and affect that actual object.


    So, with java, because it's always pass by value, but objects are never passed, is it always the case that when I do foo(obj) that obj is copied, the new reference to that object stored in a variable, and the value of that variable passed to foo?
     

    [/quote]

    Structures, By Value

    The function you called gets a copy of the data. No changes ever make it back to you.

     Structures, By Reference

    The function you called get a reference to the data. Any changes it makes are returned to you.

    Classes, By Value

    The function you called gets a copy of the pointer to the object. Any changes it makes to the object are returned to you.

    Classes, By Reference.

    The function you called gets a reference to the pointer to the object. Any changes it makes to the object are returned to you. In addition, it can change your pointer to point to an entirely difference object.

     

    Java only has "Classes by Value". It doesn't have structures, nor does it have by reference passing.

     



  • Wow. I started reading DailyWTF when I started my first job after school (as a Java developer). I am very, very happy to see that in less than one page of discussion everyone here manages to be not only clear on how Java works, but a C# and a Java developer can exchange words like adults (read: real coders). WTF? lol. Oh, and grauenwolf's post sums it up nicely, let's just not forget primitives.



  • Thanks - I didn't know there was a difference between structures by 'x' and classes by 'x'. Crystal clear now :)



  • OK, using the following test code in Java:

    // SomeObject.java
    public class SomeObject {
            public int property;
    }

    // Main.java
    public class Main {
            public static void main(String[] args) {
                    SomeObject bleh1 = new SomeObject();
                    bleh1.property = 3;
                    SomeObject bleh2 = bleh1;
                    bleh2.property = 5;
                    System.out.println(bleh1.property);
            }
    }

    Printed out 5 on my console.

    P.S. The edit box isn't letting me paste tabs, so I had to respace everything.  So, if something looks screwy, it's not my fault.



  • To anyone still confused about method calls in Java:

    Simple and concise explanation

    There are no object variables in Java, and consequently you cannot pass an object to a method. The two types of variables available are pointers and various primitive types.

    Method calls are always call-by-value, and nothing else. When you send a variable to a method, that variable's value is always copied. The local copy in the method can not affect the original variable.

    That's all.

    Implications

    • If you need to pass a reference to a primitive variable to a method, then you need to wrap it in an object.
    • If you need to "pass a copy of an object to a method" (informally speaking) and keep the original, you have to copy it yourself.

    This is because a pointer value that is passed to a method will keep pointing to the original object, since an object is never automatically copied by Java. Remember, the object isn't sent, just the pointer.

    Anyway, the problem, IMO, that is causing all these time- and energy-consuming discussions is that Java insists on calling pointers "references" (which, i believe, is far too general a word to be useful). This is merely a confusion of terminology, and inventing expressions like "call-by-reference-value" is certainly not helping. It's always call-by-value, and Java uses pointers consistently for non-primitive variables. Try saying "call-by-pointer-value" and see how silly it sounds...



  • Good summation - more proof that people shouldn't be let loose in Java / C# until they have fully grasped memory management in C.  Imagine trying to explain the semantics of passing references to pointers in c++ to them! 


Log in to reply