Beefy Boxes and Bandwidth Generously Provided by pair Networks
We don't bite newbies here... much
 
PerlMonks  

Re: self-feeding infinite loop

by bart (Canon)
on Aug 18, 2007 at 11:27 UTC ( #633462=note: print w/replies, xml ) Need Help??


in reply to self-feeding infinite loop

It's not clear to me exactly what you're trying to do, but you've sinned against a big no-no:
Do not modify an array in a foreach loop over the same array.
What I do, if I don't mind the array being eaten in the process, is something like this:
$\ = "\n"; # append newline after print @a = 'a'; while(@a) { # there's stuff left in the array my $item = shift @a; # remove it, ready to process print $item; if(rand() < 0.8) { # sometimes add a new item push @a, ('a' .. 'z')[int rand 26]; } }
Example output:
a p i n o q e p k

You see? while doesn't mind at all if the item to loop over, changes under it. foreach does.

That's one way that you can, for example, replace a recursive implementation of a file digger that does something like File::Find, with an iterative one: just push new directories you encounter while processing a directory, onto the to-do array.

Replies are listed 'Best First'.
Re^2: self-feeding infinite loop
by Dominus (Parson) on Aug 20, 2007 at 14:02 UTC
    It's not clear to me exactly what you're trying to do, but you've sinned against a big no-no:
    Do not modify an array in a foreach loop over the same array.
    I argued a few years ago on p5p that the prohibition in the manual is excessive, since the behavior is actually fairly simple and reliable. The only real problem with the technique is that, since p5p has declined to guarantee the current simple, reliable behavior, you have to worry that perhaps a future version of Perl will change the behavior.

    I tried to get p5p to agree to guarantee the current behavior, but it didn't happen.

    In former times there was a similar warning about modifying a hash in the middle of a while (each %hash) loop, even though the hash code had a special case in it to handle that exact use case, since version 5.000. The prohibition in the manual had been added later by someone with more superstition and less understanding of the actual behavior.

    A lot of stuff in the manual is like that, warning you that you must throw salt over your shoulder to avoid the wrath of the Moon God, or whatever.

    I don't think referring to warnings in the manual as "no-nos" or thinking of them in terms of "sin" is a very effective way to handle this sort of issue. We are supposed to be professional adults, not toddlers, and this is supposed to be an engineering discipline, not some mystical rite. Using the language of superstition can only promote superstitious behavior.

      So if you splice an array while using for what do you expect it to do? Especially if you splice elements such that your current index either no longer exists or is in a completly new location? More importantly how many people can agree on what the correct behavior is then?


      ___________
      Eric Hodges
        your current index either no longer exists or is in a completly new location?
        The index is a number. Numbers do not have locations, and cannot be created or destroyed, not even by the splice operator.

Re^2: self-feeding infinite loop
by spx2 (Deacon) on Aug 18, 2007 at 14:03 UTC

    on the contrary,the code i first posted , namely the first example is showing that using foreach and push works to achieve an infinite loop behaviour.

      Maybe it works, maybe it doesn't. But you're definitely in the territory of "unpredictable behaviour".
        But you're definitely in the territory of "unpredictable behaviour"

        I may be being somewhat picky (or I may even be downright wrong), but I don't see any "unpredictable behaviour" there. I agree that one needs to be careful when modifying an array by iterating over the same array, but the following does behave predictably:
        use strict; use warnings; my @array = ('a'); foreach (@array) { push @array,'a'; print"@array\n"; sleep(1); # so we can absorb what's happening }
        Cheers,
        Rob

Log In?
Username:
Password:

What's my password?
Create A New User
Node Status?
node history
Node Type: note [id://633462]
help
Chatterbox?
and all is quiet...

How do I use this? | Other CB clients
Other Users?
Others exploiting the Monastery: (3)
As of 2018-07-23 00:42 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?
    It has been suggested to rename Perl 6 in order to boost its marketing potential. Which name would you prefer?















    Results (458 votes). Check out past polls.

    Notices?