Jump to content
  • Advertisement
Sign in to follow this  
c4c0d3m0n

C++ vs Java -- const vs final

This topic is 3660 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

Hello all.. I'm still learning Java at university, although I know C++ fairly well. I've got a question about final in Java in comparisson to const in C++. Some uses of const in C++:
class Foo
{
    const int Bar( const double Naz ) const;
}

-----
const int Bar( const double Naz ) const;
^^^^^^^^^
Returns a constant int
-----
const int Bar( const double Naz ) const;
               ^^^^^^^^^^^^
Requires a constant double
-----
const int Bar( const double Naz ) const;
                                  ^^^^^
Foo::Bar() may not change the instance of Foo that it's called from
Also, Foo::Bar() may be called on constant instances of Foo
-----
In Java, I know how to use the first two with final. Is there something like the last example I gave in Java aswell? Thanks for your time

Share this post


Link to post
Share on other sites
Advertisement
The standard Java way of doing this is to return an immutable interface. Something like:


interface ImmutablePoint
{
int getX();
int getY();
}

class Point implements ImmutablePoint
{
int x, y;

int getX() { return x; }
int getY() { return y; }
}

boolean isUnderPoint(ImmutablePoint point) // 'point' cannot be chanced by this method
{
// ..
}

Share this post


Link to post
Share on other sites
Quote:
Original post by c4c0d3m0n
const int Bar( const double Naz ) const;
^^^^^^^^^
Returns a constant int

Which doesn't make much sense.

Quote:
Original post by c4c0d3m0n
const int Bar( const double Naz ) const;
^^^^^^^^^^^^
Requires a constant double

No, it doesn't. You can pass a non const double just fine because the value is copied anyway.

Note that in Java final UserType object; is somewhat like UserType * const object in C++, which means that you cannot make object point to a different Object, but you can mutate the Object that it points to.

Share this post


Link to post
Share on other sites
*grumble* This is why Java confuses me so much, pointers, references, instances, it's all one big pile of steaming foobar. I guess I'll be going back to C++ very fast after the course is over.


@DevFred
I realise it doesn't make much sense, it was more of an example to show what I meant about the different positions of const. I guess chaning all those into constant references would make more sense :)

@OrangyTang
Does this mean that I need to create two classes of everything I want to use constant references of (and effectively two *.java files)? I must say I don't really understand what the Java developers were thinking when they designed this feature... Maybe there is a good reason I'm missing.



As I understand now, when I write boolean isUnderPoint(Point p), p is automatically passed by reference (since there is no NULL pointer if I'm not mistaken). If I'd go and write boolean isUnderPoint(final Point p), it would mean that p can't point to another object, but that the current object can be changed through p (which would make p a pointer! confusing..)


Thanks for clarifying a few things, but I'm afraid I'm still a little in the dark about the Java way of things. The book that the course is built upon is not very good either (even the professor keeps complaining about it oddly enough). Is there maybe some sort of book that teaches Java to people that know C++? I can imagine I'm not the first person in this situation. I'd like to learn Java properly, as I believe a good programmer should know more than one language.

Share this post


Link to post
Share on other sites
Quote:
Original post by c4c0d3m0n
*grumble* This is why Java confuses me so much, pointers, references, instances, it's all one big pile of steaming foobar.

Actually, it is very simple in Java. Java references are a lot like C++ pointers, C++ references do not exist in Java, Classes define reference types, and everything is passed by value.

Quote:
Original post by c4c0d3m0n
when I write boolean isUnderPoint(Point p), p is automatically passed by reference (since there is no NULL pointer if I'm not mistaken).

NO! There is no pass by reference in Java, everything is passed by value. In this case, the reference p is passed by value. p is NOT a Point, it is a reference to a point. Java does not allow storing objects directly in variables (that would be value semantics), only references to objects (this is called reference semantics).

And sure there's a null pointer:

Point p = null;
p.doSomething(); // NullPointerException

Quote:

James Gosling, et al., The Java Programming Language, 4th Edition
Some people will say incorrectly that objects are passed "by reference." In programming language design, the term pass by reference properly means that when an argument is passed to a function, the invoked function gets a reference to the original value, not a copy of its value. If the function modifies its parameter, the value in the calling code will be changed because the argument and parameter use the same slot in memory.... The Java programming language does not pass objects by reference; it passes object references by value. Because two copies of the same reference refer to the same actual object, changes made through one reference variable are visible through the other. There is exactly one parameter passing mode -- pass by value -- and that helps keep things simple.

Share this post


Link to post
Share on other sites
Wow! Thanks! This really cleared up a few things!


One thing left... The quote states that having just one parameter passing mode keeps things simple... But what if I want to pass a copy of my object to a function? How would I do that? I've had situations in C++ where I had to pass a copy.

Also, why do certain built-in functions of Java give back a copy of a value instead of a reference to it? I'd actually expect Math.max( i, j ) to return i or j instead of the actual value stored inside the variable..

Share this post


Link to post
Share on other sites
Quote:
Original post by c4c0d3m0n
But what if I want to pass a copy of my object to a function? How would I do that? I've had situations in C++ where I had to pass a copy.

Well, instead of passing a reference to the original by value, you pass a reference to a clone (which you have to provide) by value.

foo.someMethod(myObject.clone());

In order for this to work, MyClass has to
- implement the interface java.lang.Cloneable
- override the clone() method
-- first call super.clone() to get a shallow (bit by bit) copy
-- then clone all fields for which a shallow copy isn't good enough

Example:
public class CloneExample implements Cloneable
{
private int i;
private boolean b;
private int[] a;
private String s;

public CloneExample clone()
{
CloneExample that = null;
try
{
// make a bit by bit copy by calling the inherited clone() method
that = (CloneExample) super.clone();

// a references the original array, so we have to manually clone it
that.a = this.a.clone();

// We don't have to clone s because Strings are immutable.
// this.a and that.a both refer to the same object, but that is no problem.
}
catch (CloneNotSupportedException e)
{
System.err.println("this shouldn't happen");
e.printStackTrace();
}
return that;
}
}



In Java, copying Objects is hard, while sharing Objects is easy. It is the opposite in C++. It's a thing you have to get used to when coming from C++ to Java. You very rarely have the need to copy objects.

Quote:
Original post by c4c0d3m0n
Also, why do certain built-in functions of Java give back a copy of a value instead of a reference to it?

Because in Java, there is no such thing as a reference to a primitive.

Quote:
Original post by c4c0d3m0n
I'd actually expect Math.max( i, j ) to return i or j instead of the actual value stored inside the variable.

What would you expect Math.max(a*b, c*d) to return then?

References in the C++ sense DO NOT EXIST in Java. (That's why the common swap function is impossible in Java.) Java has crippled pointers called references, but they have nothing to do with the references from C++. You cannot have indirections to variables in Java, only indirections to anonymous Objects.

Once again, variables NEVER store Objects directly in Java. A variable either stores a primitive, or a reference to an Object. If you pass an int, it gets passed by value. If you pass a reference, it gets passed by value. YOU CANNOT PASS OBJECTS (neither by value nor by reference), only references to objects (by value, as always).

- Cup Size -- a story about variables
- Pass-by-Value Please (Cup Size continued)
- Java is Pass-by-Value, Dammit!

Share this post


Link to post
Share on other sites
Thanks for all the info! I hope I can appreciate Java a bit more now that these unclarities have been cleared. However, I think my language of preference will stay C++ for a while, maybe untill I try my heart at another language...

Share this post


Link to post
Share on other sites
Quote:
Original post by c4c0d3m0n
I think my language of preference will stay C++ for a while, maybe untill I try my heart at another language...

1. As long as you THINK in language X, it is very hard to appreciate language Y.

2. If you already know REAL C++ (if you know what RAII and template template parameters mean, you probably do), Java may just appear like a crippled C++ to you. The interesting parts of Java are not language features, but what you can easily do with the language (multithreading, networking, portable GUIs).

3. If you want to become a better programmer, it is very important to learn new languages. If Java doesn't wow you (and it probably doesn't), I recommend Haskell (or any other functional programming language) for a completely different view on programming.

Share this post


Link to post
Share on other sites
final class cannot be subclassed.
final method cannot be overriden.
final variable can be only assigned once.

That's it. Period. As such, it's not really related to C++ const.

Java implements const semantics through immutable types, where their interface does not allow internal values to be changed (it has get(), but not set()). Final does not provide that.

Also, anything that is not a primitive type in Java is C++ equivalent of shared_ptr<T> in an application that doesn't use references or pointers in any way and passes everything by value.

Arrays are shared_ptr<vector<T>>.

Generics in Java are dynamic_cast<T>, not like templates in C++.

It really is that simple.

I'm wondering if find/replace could be used to port Java code to C++ in this way...

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

GameDev.net is your game development community. Create an account for your GameDev Portfolio and participate in the largest developer community in the games industry.

Sign me up!