~~David~~ has asked for the wisdom of the Perl Monks concerning the following question:

I have a little module that creates a hash of hashes for me. I want to pull one of the values out. When I use the code below, I get a neverending foreach loop.

If I hard-code $_ into a number, and move the print statement outside of the foreach loop, I get a real value.

When I print $_, I do get the hash keys. I don't understand what is going on.

Can anyone off some suggestions?
foreach (@files) { $file = "$klarfdir"."\\"."$_"; $file = Klarf::Parser->new($file); foreach (keys %{$file-> defectdata}){ #this never ends, but if I + print $_ only, it works fine. print ($file -> defectdata -> {$_} -> {XINDEX}); } }
~~David~~

Replies are listed 'Best First'.
Re: Neverending Foreach Loop
by GrandFather (Saint) on Jul 12, 2007 at 22:48 UTC

    $file-> defectdata looks like a function call and is likely to return something different each time it's called. Maybe what you want to do is:

    foreach (@files) { $file = "$klarfdir" . "\\" . "$_"; $file = Klarf::Parser->new($file); my %result = %{ $file->defectdata () }; foreach ( keys %result ) { print( $result{$_}->{XINDEX} ); } }

    DWIM is Perl's answer to Gödel
      That worked.
      Thank you.
      I don't understand why it returns somthing different though.
      ~~David~~

        It's a function call. Looks like it's for a parser. I'd guess each time it's called it returns a result from parsing the next "chunk". You need to read to docs for the module.


        DWIM is Perl's answer to Gödel
        Even if the contents of the hash are the same each time you call the sub, it's still a different hash. To take the most trivial example:
        sub get_hashref { my %hash; return \%hash; }
        it creates a new my %hash each time it's called, since the old one went out of scope and no longer exists1. If you want to prove this to yourself, create a trivial sub like that and call it twice, storing both hashrefs. Add some data to one hashref, then look in the other - it will still be empty.

        (There are ways to have it return references to the same hash every time it's called, such as

        my %hash; sub get_hashref2 { return \%hash; }
        but defectdata() apparently doesn't do this.)

        1 Not entirely true, in that the previous hash still exists and can be accessed by the previously-returned hashref, but it has become anonymous and is no longer my %hash. Read up on "closures" for more about how this works (and how it can be used to do some pretty powerful stuff).

Re: Neverending Foreach Loop
by runrig (Abbot) on Jul 12, 2007 at 22:38 UTC
    Since I have no idea what Klarf::Parser is (or what defectdata() returns, other than the obvious...a hash reference), I'd say do a print "$filename: $_\n"; before the other print. Of course, you'll have to save the filename instead of clobbering it into a parsed thingamabob.