Killing the comma operator

Observer via Digitalmars-d digitalmars-d at puremagic.com
Tue May 10 14:30:06 PDT 2016


On Tuesday, 10 May 2016 at 09:52:07 UTC, Mathias Lang wrote:
> So, following DConf2016, I raised a P.R. to deprecate usage of 
> the comma expressions, except within `for` loops increment [5].
> ...
> It seems there is a reasonable ground to kill it. However, 
> there have been legitimated concern about code breakage, so we 
> would like to hear from other people:
>
> Do you like comma expressions, and think its presence in the 
> language is more pro than con ?

I've programmed in C for decades, and in Perl for a decade, and 
*never*
had a problem with the comma operator in either language.  While I
haven't been part of any D-language discussions about this 
operator,
I fail to see it as causing serious code problems.

Perl in particular uses commas extensively, both as a C-type 
operator and
in list construction.  Perl is helped in that regard by 
distinguishing
scalar context (C-type operator) from list context (list argument
separator).  The fact of the matter is, anyone who learns Perl 
finds
this spectacularly unconfusing.  So perhaps a better solution than
throwing away the operator in D is to think about supporting 
proper
context-awareness.  It's been done before (as demonstrated in 
Perl)
with great success, so we definitely can't say it's an 
impossibility.
And D already understands one ubiquitous list-construction 
context,
namely the act of passing arguments to functions.

Now admittedly, there aren't too many situations where the comma 
acting
as a C-type operator finds a use.  But commas in all of the 
for-loop
control expressions, not just the increment clause, are 
definitely useful.
And more than that, they're useful whenever you want to execute 
several
independent calculations in some context that doesn't allow 
"statement
expressions".  See 
http://gcc.gnu.org/onlinedocs/gcc/Statement-Exprs.html
for how this is supported in GNU C, with a very clean syntax.  I 
would
strongly suggest that if you want to deprecate the comma operator 
for
some reason, that you build statement expressions into the 
language,
allow them in all contexts where comma operators are presently 
very
common, and document this widely as a standard idiom in the 
language.

Note that for-loops are definitely not the only places where comma
operators come in handy.  As an example, I wrote a very long 
critique
of TDPL, and sent it off to Andrei late last year.  In an item for
page 382, I provided a lot of replacement text to clarify the 
example.
Within that text was the following delegate code, showing 
excellent use
of the comma operator in a do-while loop-control context:

(i) {
     bool __done = false;
     do {
         writeln(i);
     } while (__done = true, !__done);
     // __done is still false if and only if the loop body executed
     // a break and skipped the reassignment within the while test.
     return __done ? 0 : 1;
}

That's actually rather tricky code.  In the general case for such 
a loop,
you cannot simply move the "__done = true" assignment and place 
it at the
end of the loop body, to avoid use of the comma operator.  That's 
because
the code earlier in the loop body might contain a "continue" 
statement,
and that would skip right by the assignment if it were part of 
the loop
body instead of being part of the loop-condition expression.

So whatever is done with the comma operator in D, you first need 
to
enumerate all the places where it is truly useful, and make sure 
you
support those cases well.  I find the present syntax very simple 
and
very readable, and so would be very reluctant to give it up.  If 
there
is really a need to do so, then allowing brace-enclosed statement
expressions seems to me to be a reasonable compromise, requiring 
only
clean, very little extra syntax.

If you do make this kind of transition, it needs to be spread 
across
multiple compiler releases.  In particular, you should never 
proceed
to the next stage until *all* the major compilers (DMD, GCC, LDC) 
have
caught up to the present stage.

* Release 1:  Implement statement expressions, allow them in all 
the
   right contexts, and document them.  Using this release, acquire
   real-world experience and fix any implementation bugs.

* Release 2:  Now that statement expressions are known to be
   well-supported, document them as being idiomatic in common 
contexts
   such as loop control, recommend their use, and document that 
the comma
   operator will be deprecated in future releases.  Provide a 
compiler
   option (documented but defaulted off at this stage) to warn 
about use
   of the comma operator in places where a statement expression 
would do
   the trick instead, to allow developers to quickly locate places 
that
   deserve some attention.  Make no other changes to the compilers 
at
   this stage, because it is only now that statement expressions 
will be
   known to be safe enough for general use, and you want to allow 
a period
   for pleasant, well-planned conversions before the hammer comes 
down.

   Also in this timeframe, see if dfix can be equipped to handle 
such
   conversions automatically.

* Release 3:  Still allow the comma operator, but now default the
   comma-operator deprecation warning to be on.  And declare in the
   documentation that this is the case, and that this will be the 
last
   release in which the comma operator is still allowed.

* Release 4:  Obsolete the comma operator entirely.  Have the 
compiler
   generate an error, aborting the compilation, instead of a 
warning,
   if comma operators are found during compilation.

* Release 5:  Finally allow the language definition to re-use the 
comma
   for other purposes (tuple construction, or whatever).

A slow evolution like that is the only sane way to proceed.  But 
again,
that's only if context-awareness is not possible, and I find that 
hard
to believe.


More information about the Digitalmars-d mailing list