[Nickle]Sequencing of expressions with side effects

Bart Massey nickle@nickle.org
Tue, 23 Jul 2002 12:55:20 -0700


In message <E17X3qI-0000dh-00@localhost> you wrote:
> 
> Around 10 o'clock on Jul 23, Bart Massey wrote:
> 
> > Naah.  If you're gonna honor the precedence of operators in
> > expression evaluation, you should also honor the
> > associativity: assignment operators associate right-to-left,
> > and should thus evaluate right-to-left.
> 
> I disagree.  A strict left to right rule fixes problems with lexical scope 
> of identifiers:
> 
> 	a = (int b = 2) ** b;

Huh?  The example you give has nothing to do with the order
of evaluation of assignment, as near as I can tell: the
exponentiation is higher-precedence than the assignment, so
the RHS ((int b = 2) ** b) evaluates however it evaluates,
and the result is bound to a.  This will happen whether you
evaluate assignment left-to-right or right-to-left.  The
inner assignment is similar.  Perhaps you're making the
point that parentheses should still dominate the order of
evaluation: a parenthesized expression should be fully
evaluated before use.

Or perhaps you meant to write

	b = (int b = 2) ** 2

which I agree is quite confusing, but IMHO unavoidable: see
below.

> Associativity only affects implicit parenthesization, I don't think it 
> should affect the evaluation order.

I guess my rules are ultimately these:

1. The meaning of an expression should never be changed by
   explicitly putting in the parentheses implied by
   precedence and associativity.

2. Expression evaluation should honor explicit parentheses:
   parenthesized subexpressions should always be evaluated
   before their containing expressions.

I think these two rules together are sufficient to
completely constrain Nickle's order of evaluation in
expressions, and they are easy to implement and understand.

The only problem I see is that they lead to a little bit of
wartiness as discussed above: I find this NBD compared to
the alternatives.

> >   a += b --> a = (int x1 = a) + (int x2 = b);
> > which would still be consistent with the principles
> > espoused above.
> 
> This isn't quite right -- 'a' must be evaluated only once in the 'a += b' 
> case:
> 
> 	a += b		-> 	(poly* ap = &a), (*ap = *ap + b)

Since a is required to be an lvalue, I'm not seeing how this
matters.  Maybe when a is of pointer type?

	Bart