Beefy Boxes and Bandwidth Generously Provided by pair Networks
Perl-Sensitive Sunglasses
 
PerlMonks  

Re^2: Puzzling $| behavior

by blokhead (Monsignor)
on Oct 08, 2007 at 05:23 UTC ( #643387=note: print w/ replies, xml ) Need Help??


in reply to Re: Puzzling $| behavior
in thread Puzzling $| behavior

(please correct here me if I'm wrong)
I don't know if perl's documentation defines (as a feature) the order in which arguments are evaluated, but it's simple to check that it really does evaluate them in left-to-right order:
$ perl -le 'print sub{print 1; "x"}->(), sub{print 2; "y"}->()' 1 2 xy
The reason the OP's example is weird is because Perl's argument passing uses aliases whenever possible (as ikegami illustrates below). In the example, an alias to $| gets passed as the second argument. When evaluating the fourth argument, $| is changed. When print finally inspects its arguments, the aliased second argument will report the changed value.

blokhead


Comment on Re^2: Puzzling $| behavior
Download Code
Re^3: Puzzling $| behavior
by ikegami (Pope) on Oct 08, 2007 at 05:54 UTC

    I don't know if perl's documentation defines (as a feature) the order in which arguments are evaluated

    It's not, but no one has mentioned a system or version where the arguments are evaluated in any order other than left-to-right in past discussions on the subject.

    It's technically subject to change since it's not documented, but I find it highly unlikely to change in Perl5.

      ikegamino one has mentioned a system or version where the arguments are evaluated in any order other than left-to-right

      My answer to the OP was completely wrong,
      which is what I found out after investigating
      into the topic.

      Thats another case where prejudice brings ill-fated conclusions.
      One simple look into perl -MO=Bblock thisprog.pl reveals
      the left-to-right sequence
      OP (0x824dc78) enter COP (0x81f30f0) nextstate SVOP (0x824daa0) const [6] IV (0x8167cdc) 1 PADOP (0x8193748) gvsv GV (0x816887c) *| BINOP (0x8189228) sassign COP (0x824c460) nextstate OP (0x824ffa8) pushmark SVOP (0x81892b8) const [7] PV (0x8168804) "first=" PADOP (0x818c5c0) gvsv GV (0x816887c) *| SVOP (0x818dc50) const [8] PV (0x8168810) " second=" PADOP (0x824fdb8) gvsv GV (0x816887c) *| UNOP (0x824fc80) postinc [4] SVOP (0x824dc58) const [9] PV (0x81688a0) "\n" LISTOP (0x824ff80) print LISTOP (0x824d8e0) leave [1]
      int the perl. Sorry, I was mistaken by the way one
      "programs" Perl in C via its interfaces.

      Thanks to all people who helped clearing this up.

      I will eventually make an addendum to my first post.

      Regards

      mwa
      i think it's matter of the compiler optimizer:
      if i have something like f($x+=2, $x+=3); (and comma between arguments is not a sync point, like in C) then the optimizer could collapse $x+=2 and $x+=3 to $x+=5. It's not only matter of order.

      $_ = 1; f($_+=2, $_+=3); sub f { print shift, ", ", shift, "\n"; } print `perl -v`; __________ 6, 6 This is perl, v5.6.0 built for darwin ....
      Oha

        It's not because of an optimization.

        # $_ $_[0] $_[1] $_[0] $_[1] # ----- ----- ----- ----- ----- $_ = 1; # 1 do { # local @_; # alias $_[0] = $_+=2; # 3 $_ 3 alias $_[1] = $_+=3; # 6 $_ $_ 6 6 &f; };

        Add $_++; to f and you'll see it print 7, 7 because $_[0] and $_[1] are aliased to $_.

        It works that way because += returns its LHS as an lvalue.

        >perl -le "$_=1; ($_+=2)+=3; print $_" 6

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: note [id://643387]
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others examining the Monastery: (14)
As of 2014-09-16 13:39 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    How do you remember the number of days in each month?











    Results (24 votes), past polls