From: Tom McGlynn on
On Nov 5, 12:59 am, Roedy Green <see_webs...(a)mindprod.com.invalid>
wrote:
> On Wed, 4 Nov 2009 13:06:20 -0800 (PST), laredotornado
> <laredotorn...(a)zipmail.com> wrote, quoted or indirectly quoted someone
> who said :
>
> >while ((line = reader.readLine()) != null) {
> > stringBuf.append(line + "\n");
> >}
> [code edited for appearance]
> >saying, "Avoid assignments in operands". How would I rewrite the
> >while loop to make this error go away but achieve the same
> >functionality?
>
> That code is fine. There is really no other way to do it. However in
> general it is confusing to newbies if you write code of the form:
>
> x = ( a = b ); // = assignment embedded in expression.
> as opposed to
> x = ( a == b );
> --
> Roedy Green Canadian Mind Productshttp://mindprod.com
>
> An example (complete and annotated) is worth 1000 lines of BNF.

The problem with this idiom for me is that you have a choice of either
having a statement that has side effects, e.g., the original code, or
you need to duplicate the read statement. While both of these are
legal I don't like either. They both seem inelegant. Using the for
statement as Lew suggested at least makes sure that the two reads are
close together. This idiom is pretty common and I wonder if it's
worth considering a little bit of syntax that would allow (imho)
cleaner code.

Perhaps something equivalent to the for loop where the action that
takes place at the bottom of the loop in a standard for loop takes
place at the top of the loop. I.e.,
for (a; b; c) {d}
is equivalent to
{
a;
while (b) {
d;
c;
}
}

If we extended the while loop where

while(a; b; c) {d}

is rendered as

{
a;
while (1) {
b;
if (c) {
d;
} else {
break;
}
}
}

Then the original request becomes

while(; line=reader.readLine(); line != null) {
...
}
which avoids both the statement with side effects and duplication
of the readLine().

Of with all three clauses

while (Reader r = getReader(); line=r.readLine(); line != null) {

I think I would use such this rather often were it available. Has
such a construct been implemented in other languages or proposed for
Java?

Regards,
Tom McGlynn
From: Lew on
Roedy Green wrote:
> On Wed, 4 Nov 2009 13:06:20 -0800 (PST), laredotornado
> <laredotornado(a)zipmail.com> wrote, quoted or indirectly quoted someone
> who said :
>
>> hile ((line = reader.readLine()) != null) {
>> stringBuf.append(line + "\n");
>> }
>>
>> saying, "Avoid assignments in operands". How would I rewrite the
>> while loop to make this error go away but achieve the same
>> functionality?
>
> That code is fine. There is really no other way to do it. However in
> general it is confusing to newbies if you write code of the form:

The code isn't necessarily fine. It puts the scope of 'line' outside the
loop, where in most cases it should be confined to the loop.

There is really another way to do it, posted about eight hours prior to your
post and quoted by the OP. This other way confines the scope of 'line' to the
loop.

--
Lew
From: Lew on
Tom McGlynn wrote:
> The problem with this idiom for me is that you have a choice of either
> having a statement that has side effects, e.g., the original code, or
> you need to duplicate the read statement. While both of these are
> legal I don't like either. They both seem inelegant.

"Seem" being the operative term.

There's nothing wrong with writing the 'readLine()' assignment twice, since
that is what purchases the scope confinement for the 'line' variable.

--
Lew
Don't quote sigs.
From: Patricia Shanahan on
Tom McGlynn wrote:
> On Nov 5, 12:59 am, Roedy Green <see_webs...(a)mindprod.com.invalid>
> wrote:
>> On Wed, 4 Nov 2009 13:06:20 -0800 (PST), laredotornado
>> <laredotorn...(a)zipmail.com> wrote, quoted or indirectly quoted someone
>> who said :
>>
>>> while ((line = reader.readLine()) != null) {
>>> stringBuf.append(line + "\n");
>>> }
>> [code edited for appearance]
>>> saying, "Avoid assignments in operands". How would I rewrite the
>>> while loop to make this error go away but achieve the same
>>> functionality?
>> That code is fine. There is really no other way to do it. However in
>> general it is confusing to newbies if you write code of the form:
>>
>> x = ( a = b ); // = assignment embedded in expression.
>> as opposed to
>> x = ( a == b );
>> --
>> Roedy Green Canadian Mind Productshttp://mindprod.com
>>
>> An example (complete and annotated) is worth 1000 lines of BNF.
>
> The problem with this idiom for me is that you have a choice of either
> having a statement that has side effects, e.g., the original code, or
> you need to duplicate the read statement. While both of these are
> legal I don't like either. They both seem inelegant. ...

Just for completeness, here are a couple more options, each with its
own inelegance.

Repeat the test:

String line;
do {
line = reader.readLine();
if(line != null) {
stringBuf.append(line + "\n");
}
} while (line != null);

Use break:

while(true) {
String line = reader.readLine();
if(line == null){
// End of input
break;
}
stringBuf.append(line + "\n");
}

I don't recommend either of these - in my own code I use the original
version, despite generally disliking side effects that are not at the
top level. I think that particular construct is an idiom most Java
programmers have seen and will understand without difficulty.

Patricia
From: Tom McGlynn on
On Nov 5, 9:21 am, Lew <no...(a)lewscanon.com> wrote:
> Tom McGlynn wrote:
> > The problem with this idiom for me is that you have a choice of either
> > having a statement that has side effects, e.g., the original code, or
> > you need to duplicate the read statement. While both of these are
> > legal I don't like either. They both seem inelegant.
>
> "Seem" being the operative term.
>
> There's nothing wrong with writing the 'readLine()' assignment twice, since
> that is what purchases the scope confinement for the 'line' variable.
>

For me duplication of code is almost always inelegant and even
slightly dangerous. There's always the chance that there could be
unintended inconsistencies between the two instances--especially when
code gets modified. I make no claim that this is a massive issue, but
neither is the suggested change very large. As with the for
statement it allows restricting the scope of the variables used in
the loop. Given that it's not currently valid it is naturally less
familiar than currently legal idioms. The particular syntax I used is
the result of at least 30 seconds of thought: there is likely
something better, I was interested in the idea not the particular
implementation.

The proposal would address a fairly broad class of loops: whenever the
loop is to be terminated based upon some expression, and the value of
that expression is also needed within the loop.

Regards
Tom McGlynn