Commenting in Java

E

Eric Sosman

Mike said:
Yes, yes, yes. People who judge programming languages by how few keystrokes
each requires miss this. The "every string means *something*"-ness of C is
one of its biggest drawbacks.

Huh? Are you advocating for languages that require
meaningless constructs? I can see the messages now:

Meaningful.java:42: method 'toString' has too
much meaning; add useless fluff

Important.java:13: 'import' statement has too
much import

Singleton.java:98: missing required call to
java.lang.fluff.AiryPersiflage.noOperation() in
empty private constructor
 
M

Mike Schilling

Eric Sosman said:
Huh? Are you advocating for languages that require
meaningless constructs?

You're joking, right?

I'm suggesting that

*x+=y=12?5^7:y-=2

be the syntax error God meant it to be.
 
T

Tor Iver Wilhelmsen

Mike Schilling said:
*x+=y=12?5^7:y-=2

Hey, never underestimate the power of illegible code to keep a
programmer in employment.

"We cannot fire him, he's the only one who understands the magic of
the payroll algorithms!"

:)
 
E

Eric Sosman

Mike said:
You're joking, right?

I'm suggesting that

*x+=y=12?5^7:y-=2

be the syntax error God meant it to be.

It's not a syntax error; it's just a vastly stupid
way to write `*x += y = 2'.

Oddly enough, it's also not a syntax error in Java
(once you discard the leading `*' or replace it with an
approximate Javoid equivalent):

x.val+=y=12?5^7:y-=2

is just a vastly stupid way to write `x.val += y = 2'.

Conclusion: Java is no improvement on C.

<... dons asbestos suit, runs for cover ...>
 
M

Mike Schilling

Eric Sosman said:
Mike Schilling wrote:

It's not a syntax error; it's just a vastly stupid
way to write `*x += y = 2'.

Oddly enough, it's also not a syntax error in Java
(once you discard the leading `*' or replace it with an
approximate Javoid equivalent):

x.val+=y=12?5^7:y-=2

is just a vastly stupid way to write `x.val += y = 2'.

Conclusion: Java is no improvement on C.

It's *some* improvement: At least

if (x = 2)

doesn't compile.
 
M

Monique Y. Mudama

It's *some* improvement: At least

if (x = 2)

doesn't compile.

They just pushed the problem[*] onto another data type. This compiles:


public class BooleanEquals
{
public static void main (String[] argv)
{
boolean a = false;
if (a = true)
System.out.println ("Compiles");
}
}

[*] Of course, not everyone would call this a problem ...
 
A

Andrea Desole

Chris said:
Agreed, but you seem to be assuming that the comments are going to be wrong
(significantly) more often than the code. IMO, this is only true of
incompetent programmers (as a matter of definition, rather than an observed
correlation).

no, that's not really what I meant. I just wanted to point out the
drawbacks of comments

With redundancy, you know that something is wrong (but not what). Without
redundancy then there is no hint that anything is wrong. Which would you
prefer ? If the divergence is due to mistakes in the code in a large fraction
of cases, then that warning flag is valuable. (Of course, if the mistake /is/
usually in the comment, then that doesn't hold).

well, if you are talking about a general habit, I absolutely agree.
 
T

Thomas Hawtin

Monique said:
It's *some* improvement: At least

They just pushed the problem[*] onto another data type. This compiles:
[...]
if (a = true)
[...]
[*] Of course, not everyone would call this a problem ...

Sure it's a problem. Using == true or == false isn't a particularly
direct way of expressing an expression.


It's still daft that a syntax for pointer and bit bashing with minor
concession to procedures should be used for a highish-level, OOish
language with no pointer arithmetic and little interest in bit bashing.

Tom Hawtin
 
M

Monique Y. Mudama

Monique said:
They just pushed the problem[*] onto another data type. This compiles:
[...]
if (a = true)
[...]
[*] Of course, not everyone would call this a problem ...

Sure it's a problem. Using == true or == false isn't a particularly
direct way of expressing an expression.

Wait; you're saying that the compiler shouldn't allow an equivalence
operator in a conditional? That seems a bit extreme.

Even in the case of assignment to a boolean, I'm not sure the compiler
should disallow this (if it even could). I don't think compilers
should enforce coding styles.
It's still daft that a syntax for pointer and bit bashing with minor
concession to procedures should be used for a highish-level, OOish
language with no pointer arithmetic and little interest in bit bashing.

Okay, now you've lost me completely. I'm honestly not sure what you
mean by this in the context of whether the above statement should
compile.
 
M

Mike Schilling

Monique Y. Mudama said:
Monique said:
They just pushed the problem[*] onto another data type. This compiles:
[...]
if (a = true)
[...]
[*] Of course, not everyone would call this a problem ...

Sure it's a problem. Using == true or == false isn't a particularly
direct way of expressing an expression.

Wait; you're saying that the compiler shouldn't allow an equivalence
operator in a conditional? That seems a bit extreme.

I wouldn't say that, but I would say that

if (a == true)

being merely a verbose way of saying

if (a)

is very uncommon (and should be less common still) compared to, say

if (i == 0)

So Java, which allows the typo to compile correctly only for booleans, is a
big improvement over C in that respect.
 
O

Oliver Wong

Roedy Green said:
I am more of Patricia's comment first school too. Get very clear on
just what the method will and will not do before you write it. That
will save you from the temptation of inserting bits of housekeeping
where they don't logically belong but have to go somewhere.

A somewhat effective practice I've seen, when you have a "lead
programmer/designer" (i.e. the person who knows what the program is supposed
to do), and several other programmers, is to have the lead just write
classes with methods signatures fully defined and JavaDocs explaining what
the method is supposed to do, leaving the bodies blank.

These source files can then be distributed among all the programmers,
who just read the JavaDoc to figure out what the method is supposed to do,
and then they actually write the code that does just that. If they don't
have enough information to write bodies of the method, then the JavaDoc
wasn't clear enough.

You can combine unit testing too. After the javadocs are written, but
before the method bodies are written, distribute the sourcefiles to all the
programmers, and have them all write unit tests based on the description
from the JavaDocs. Then shuffle the source files around so that every
programmer now has a different one, and then let them write code for this.

The idea is that the person who wrote the JavaDoc and the unit test is
NOT the same as the person who actually implemented the method. Ideally, the
person who JavaDoc should be the person writing the unit test, but in
practice there may be time restrictions that force us to make the unit test
writing a distributed job.

- Oliver
 
O

Oliver Wong

Chris Uppal said:
Agreed, but you seem to be assuming that the comments are going to be
wrong
(significantly) more often than the code. IMO, this is only true of
incompetent programmers (as a matter of definition, rather than an
observed
correlation).

I actually encountered a case of wrong comments which was "nobody's
fault". Can't remember the specifics, but it was something to do with
non-locality of the comment. That is, the comment talked about not only the
code that was next to it, but also about the code that laid in another file
far away.

The comment was something along the lines of "This has to be done this
way, because method 'foo' is assumes 'bar' in another file".

Of course, someone changed method foo so that it no longer assumes bar,
but never saw this comment (probably never even opened the file that
contained this comment), and so it was never updated.

Really, I don't think any one particular programmer is to be blamed (or
accused of incompetence) in this scenario. The error just sort of "evolved"
out of successive refactoring of this very large application.

- Oliver
 
O

Oliver Wong

Mike Schilling said:
I wouldn't say that, but I would say that

if (a == true)

being merely a verbose way of saying

if (a)

Not sure about this, but there may be a slight semantic difference
between the two with Java 1.5's unboxing. In particular, consider:

Boolean a = null;

if (a == false) //this is a false statement, a != false, a == null.
if (!a) //this may be a true statement, not sure. Does "null" get unboxed
into being "false"?

I guess I could actually plug this into Eclipse and find out, but I'm
feeling lazy right now.

- Oliver
 
T

Thomas Hawtin

Oliver said:
if (a == false) //this is a false statement, a != false, a == null.
if (!a) //this may be a true statement, not sure. Does "null" get unboxed
into being "false"?

If you unbox null, you get an NPE.

I believe in C# you get false/0/0.0/'0', which is great for masking bugs.

Tom Hawtin
 
M

Monique Y. Mudama

I wouldn't say that, but I would say that

if (a == true)

being merely a verbose way of saying

if (a)

is very uncommon (and should be less common still) compared to, say

if (i == 0)

So Java, which allows the typo to compile correctly only for booleans, is a
big improvement over C in that respect.

I'll buy that.
 
M

Mike Schilling

Thomas Hawtin said:
If you unbox null, you get an NPE.

I believe in C# you get false/0/0.0/'0', which is great for masking bugs.

I think C# acts like Java here..

using System;

class A
{
public static void Main()
{
try
{
Object o = null;
bool b = (bool)o;
Console.WriteLine(b);
}
catch(Exception ex)
{
Console.WriteLine(ex);
}
}
}

results in

System.NullReferenceException: Object reference not set to an instance of an
object.
 
C

Chris Uppal

Oliver said:
The comment was something along the lines of "This has to be done this
way, because method 'foo' is assumes 'bar' in another file".

Of course, someone changed method foo so that it no longer assumes
bar, but never saw this comment (probably never even opened the file that
contained this comment), and so it was never updated.

Really, I don't think any one particular programmer is to be blamed
(or accused of incompetence) in this scenario. The error just sort of
"evolved" out of successive refactoring of this very large application.

That's an interesting scenario. I agree that it would be wrong to talk of
"incompetence", but I wouldn't go so far as to say that there was no blame
involved. It's impossible (for me, here) to say /who/ should be blamed, but
I'm fairly sure that a close look would show that /someone/, not necessarily
any single programmer (it could be a management failing, for instance, or the
result of bad company culture), would be shown not to be doing a good job.

The real problem here is that either:

a) the dependency should not have been introduced
or:
b) if the dependency was unavoidable, then the comment was in the wrong
place.

I.e. it was either failing of design, or of communication -- in either case it
was an actual /failure/, not "just one of those things".

Ideally, the programmer(s) who introduced the dependency should have been able
to change the stuff that it depended on in such a way as to remove the need for
it (some sort of refactoring). Of course that might have been impossible for
technical reasons, or it may have been impractical for project management
reasons (the "other" code was already frozen, perhaps). But notice that if
there was a technical solution that was not taken for "non-technical" reasons,
then that is clearly a failure of management (in the wide sense, including the
programmers as well as the actual Managers).

If a correct coding change was not introduced (for whatever reason), then
putting the explanatory comment in the dependent code was almost exactly the
wrong thing to do (not quite, because even a mis-positioned comment /might/ be
useful). Properly, the comment should have been added to the code with the
hidden dependent: "don't change this without corresponding modifications to
xxxx". More generally, the people who "owned" the dependent code should have
talked to the people who owned the other code (they could be the same people of
course, but in that case I don't see a problem with putting the comment where
it should have been). The owners of the "other" code could have recorded the
dependency in their design documents (if any -- I'm not a big fan of them
myself); in their collective memory; or as a comment in the development branch
of the code in question (assuming the release branch was frozen).

So I'd say there was definitely a blameworthy failure somewhere. It might be
no big deal (you didn't say how serious the consequences of the mixup were),
possibly not even worth as much discussion as I've just typed in. But if the
consequences were severe, or if they could have been severe, then I'd say that
the failure was also severe, and -- although throwing words like "blame" about
might be counterproductive -- there would still be an obvious problem in the
dev group's working practises that should be identified and (if possible)
corrected.

-- chris
 
M

Monique Y. Mudama

If a correct coding change was not introduced (for whatever reason),
then putting the explanatory comment in the dependent code was
almost exactly the wrong thing to do (not quite, because even a
mis-positioned comment /might/ be useful). Properly, the comment
should have been added to the code with the hidden dependent: "don't
change this without corresponding modifications to xxxx". More
generally, the people who "owned" the dependent code should have
talked to the people who owned the other code (they could be the
same people of course, but in that case I don't see a problem with
putting the comment where it should have been). The owners of the
"other" code could have recorded the dependency in their design
documents (if any -- I'm not a big fan of them myself); in their
collective memory; or as a comment in the development branch of the
code in question (assuming the release branch was frozen).

What about the case of the API Calendar class? January is 0. We had
a bug because another API we're using assumed January would be 1. So
I put a comment in our code explaining what was going on, and some
math so that no matter what the Java API thought January should be, it
would be 1 to the other API.

This case was relatively straight-forward in that at least I could
make the code normalize January, no matter what Java thought it should
be.
 
C

Chris Uppal

Monique said:
[me:]
If a correct coding change was not introduced (for whatever reason),
then putting the explanatory comment in the dependent code was
almost exactly the wrong thing to do [...]

What about the case of the API Calendar class? January is 0. We had
a bug because another API we're using assumed January would be 1. So
I put a comment in our code explaining what was going on, and some
math so that no matter what the Java API thought January should be, it
would be 1 to the other API.

I don't see anything wrong with that. The comment was definitely called for,
and you put it in the right place.

I can (I think) see why you ask -- in both cases there is a situation where
changes to one bit of code would break another, not obviously related, system.
But in the case I was talking about, the problem was that it was (or should
have been) part of the job of the maintainers of one system to ensure that they
didn't break the other one. That doesn't hold in the case of Sun's Java
programmers -- it is no part of their job to ensure that /your/ (your
specific) system doesn't break when they make changes. Of course, it is
part of their job to ensure that users' code /in general/ doesn't break, but if
your code depends on some non-obvious (and not documented) aspect of the way
their code behaves, then that's your problem, not theirs. Hence any comments
explaining such dependencies belong in your code, not theirs.

Myself, I wouldn't have bothered with the normalisation code (though it's good
that you included an explanation of what it was for), since I don't think that
kind of detail is likely to change in later releases of the JDK. In fact I'd
worry more about the "other API" changing in future -- although I wouldn't
actually /expect/ that to happen either. But still, the idea is good, even if
I don't think it was necessary in this case.

-- chris
 

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

Forum statistics

Threads
473,982
Messages
2,570,185
Members
46,737
Latest member
Georgeengab

Latest Threads

Top