in reply to Will "$_[0]=shift" always resolve shift first?

is this reliable?

Yes.

There's quit some code on CPAN that relies on the relative order of execution, und such things aren't changed without a very good reason. The ports want to use CPAN, not break it.

  • Comment on Re: Will "$_[0]=shift" always resolve shift first?

Replies are listed 'Best First'.
Re^2: Will "$_[0]=shift" always resolve shift first? (irony)
by tye (Sage) on Sep 10, 2008 at 15:22 UTC

    Above, moritz says:

    und such things aren't changed without a very good reason

    Elsewhere in this thread, moritz offers the following aside:

    (perltrap documents that the RHS is evaluated first, btw).

    And let us see what perltrap actually says

    LHS is evaluated first in perl4, second in perl5; this can affect the relationship between side-effects in sub-expressions.

    So it appears there must have been a very good reason found when Perl5 was produced?

    In any case, we now have documentation of the evaluation order of the sides of assignment expressions. This will cause many to feel more justified in relying on this order. Of course, the documentation is actually documentation of this order having already changed (with no motivation mentioned and I'd bet money on the motivation being "it was convenient to implement that way" because that is how little justification is needed for one to change the order of evaluation of sub-expressions and exactly why it is unwise to rely on such things). So I find this documentation to be justification for not relying on the "current" order of evaluation (and I suspect that part of the point of Perl 6 will mean that this order is likely to be less "constant" in Perl 6).

    To be fair to moritz, the above node was posted before the one containing the aside (which also appears to backpedal significantly on the above simple, bold proclamation). But I felt the above simple, bold proclamation deserved a direct reply (including a link to the backpedaling).

    Also, the claim that documented behavior of local($foo)= $foo; and my $bar= $bar; requires the "current" order of evalatution is quite bogus. Indeed, that behavior for local didn't change between Perl4 and Perl5 but the order of evaluation did, QED.

    You can always evaluate the RHS and push the resulting value(s) onto the stack before you do anything with the LHS or after you've done everything to the LHS except for actually assigning the computed values over. The main determination as to what order you do those in is which way is more convenient for those results to appear on the stack.

    Now, if Perl6 makes the mistake (IMHO) of allowing context (of the RHS of an assignment statement) to be ambiguous at compile time, then this would finally force the implementors' hands on this order of evaluation issue. It would also require changing away from the "current" Perl5 order of evaluation. More likely, being able to optimize (one of the core motivations for Perl6) almost always also means being able to change a lot of order of evaluation "decisions" pretty much willy-nilly. That is, some subtle change to code not even obviously connected to the assignment statement could change the order of evaluation. In Perl 6, there should even be the possibility of both sides being evaluated "at the same time" or interleaved.

    - tye        

      So it appears there must have been a very good reason found when Perl5 was produced?

      I didn't think of major releases when I wrote that. If you sacrifice backwards compatibility anyway, (and I believe that the introduction of perl 5 did, but I'm too young to have been hacking at that time), any valid reason is good enough IMHO.

      Also, the claim that documented behavior of local($foo)= $foo; and my $bar= $bar; requires the "current" order of evalatution is quite bogus. Indeed, that behavior for local didn't change between Perl4 and Perl5 but the order of evaluation did, QED.
      Indeed, in these cases it's not really the order of evaluation that matters, but the scope. The scope of a my variable starts at the end of the statement in which it is declared, which you can easily test like this:
      $ perl -Mstrict -e 'my $x = $x' Global symbol "$x" requires explicit package name at -e line 1.
      Now, if Perl6 makes the mistake (IMHO) of allowing context (of the RHS of an assignment statement) to be ambiguous at compile time

      In Perl 6 it is known at parse time if an assignment is in list context of item context, if that is what you mean. And it has to be, because the list assignment infix:<=> has a different precedence than the item assignment infix:<=> operator, which allows for the magic of my @x = 1, 2, 3; and $x = 1, $y = 2 both to do what you mean.