Beefy Boxes and Bandwidth Generously Provided by pair Networks
Clear questions and runnable code
get the best and fastest answer

For loop problem

by srawls (Friar)
on Jun 03, 2001 at 22:24 UTC ( #85347=perlquestion: print w/replies, xml ) Need Help??
srawls has asked for the wisdom of the Perl Monks concerning the following question:

I was working on some obfuscated code, and came across a problem. Well, first what I was trying to do was to do something 12 times (i.e. for(1 .. 12)). I tried this:
for(++$....$.++.$.) {print "$_\n"}
And to my surprise it printed 2 through 12. Before I move on, I'll explain what I think should happen. To do this, I'll clean up the formatting a bit:
for(++$. .. $.++ . $.) #note before I had used ... instead of ..
Now, let's examine those values:
++$. = 1 $.++ . $. = 12 #the concatenation of 1 and 2.
So, I tried to take it apart and see which individual element was causing the problem, and eventually I came up with this:
for(++$....$..$.) #note took out the second ++
Now it prints 1 through 11, exactly what I expect. What I think is happening is that the second ++ is effecting the value of $. somehow, before it's supposed to.

This is really baffaling me, so any help is appreciated,

The 15 year old, freshman programmer,
Stephen Rawls

Replies are listed 'Best First'.
Re: For loop problem
by bikeNomad (Priest) on Jun 03, 2001 at 22:44 UTC
    You're looking at execution order for the '..' operator:
    ++$. .. $.++ . $.
    There's no guarantee as to which operand of the operator gets evaluated first. In this case, it appears to be the RHS ($.++ . $.). So you get '12', but you leave $. at 2. Then the loop happens.
      Ok, thanks bikeNomad, that does make sense. What I'm still confused at, though, is how the interperter decides the order it evaluates in. Here are a few test cases:
      When I use this is evaluates the left side first, and cycles through 1 to 11.
      But as soon as I add that second ++, it evaluates the right side first, and cyles through 2 to 12.
      And this is perhaps the strangest of them all. It evaluates the right side of the ...(flip flop) operator first, and also evaluates the right side of the . (concatanation) operator first. It cycles through 2 to 22.

      The 15 year old, freshman programmer,
      Stephen Rawls
        The problem is that the list ($a .. ++$a) is not evaluating a list like you think it is. It is not doing:
        $start = $a; $end = ++$a; for ($_ = $start; $_ <= $end; $_++) { ... }
        But rather, it is evaluating its endpoints, and then constructing the list from that. That is the cause of your problem:
        for (++$x .. $x++ . $x) { ... } # starting at ++$x # ending at $x++ . $x # THE END HAS MODIFIED THE START
        You can witness a similar result from:
        print ++$x, ++$x, ++$x; # 333
        You see, the arguments to a function aren't copies of the variables, but rather aliases -- by modifying ONE of the $x's, you've modified the others as well.

        Knowing this, the output of this program makes sense to me:

        $x = 3; print ++$x/$x--; # 3/4 => 0.75
        Why is that? Well, the numerator is ++$x, and the denominator is $x--; but in subtracting 1 from $x in the denominator, we have now altered the numerator back to its original state!

        I've worked out a solution to your 1 .. 12 loop, then.

        for (++$x .. $x++ . $x--) { ... } # or for (++$....$.++.$.--) { ... }
        See if you can work out why the starting point is 1.

        japhy -- Perl and Regex Hacker
Re: For loop problem
by MeowChow (Vicar) on Jun 03, 2001 at 23:45 UTC
    This issue was previously discussed here. Dominus' explanation was very illuminating.
                   s aamecha.s a..a\u$&owag.print
Re: For loop problem
by srawls (Friar) on Jun 03, 2001 at 22:31 UTC
    As an update to my post:

    Even more baffaling is this:

    If you change the first ++ to be a postincrement instead of a preincrement, it prints 0 to 12, just what I would expect, but still not my desired 1 to 12.

    More baffled than ever:
    The 15 year old, freshman programmer,
    Stephen Rawls

Log In?

What's my password?
Create A New User
Node Status?
node history
Node Type: perlquestion [id://85347]
Approved by root
and all is quiet...

How do I use this? | Other CB clients
Other Users?
Others pondering the Monastery: (6)
As of 2018-01-16 09:56 GMT
Find Nodes?
    Voting Booth?
    How did you see in the new year?

    Results (176 votes). Check out past polls.