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

I'm tryin to access the values in this hash. As you can see, it contains 4 array references. I'd like to access the entire arrays and the individual values in the arrays.
%HASH = { 1 => \@ARRAY1, 2 => \@ARRAY2, 3 => \@ARRAY3, 4 => \@ARRAY4, };

Replies are listed 'Best First'.
Re: Help with references
by BrowserUk (Patriarch) on Oct 23, 2003 at 02:40 UTC

    Your first problem is that your syntax for initialising a hash is wrong. It should be (at minimum):

    %HASH = ( # << note the parens not curlies. 1 => \@ARRAY1, 2 => \@ARRAY2, 3 => \@ARRAY3, 4 => \@ARRAY4, );

    Take a look at References quick reference for the definitive guide to using references and come back with any specific questions that remain or arise.


    Examine what is said, not who speaks.
    "Efficiency is intelligent laziness." -David Dunham
    "Think for yourself!" - Abigail
    Hooray!

Re: Help with references
by Zaxo (Archbishop) on Oct 23, 2003 at 02:40 UTC

    As individual elements: $HASH{$key}[$index], as whole arrays: @{$HASH{$key}}, as all one list: map {@$_} @HASH{1..4}. See tye's References quick reference.

    After Compline,
    Zaxo

      As individual elements: $HASH{$key}[$index]
      The sames values will be returned if you use $HASH{$key}->[$index]. I find this rather confusing. I looked at References quick reference and saw where tye said If the reference is in a hash or an array (and you are getting back a scalar), then you can drop the -> between the adjacent [0] and/or {KEY} parts. I'm just curious why this doesn't raise any sort of exception and if there is a correct or preferred version of the syntax?

        Either is correct. Since hash values must be scalars, perl can intuit the need to dereference for extra indexes or keys beyond the leftmost. Preference is strictly personal - use which syntax you like better.

        After Compline,
        Zaxo

        Preferred syntax? This is Perl, TMTOWTDI. That is, there is no preferred anything. There are, perhaps, caveats and some no-nos and some performance variations on occasion, but beyond this, do things the way you like. In this case, it's all syntactic sugar, so the interpreter ends up seeing the same thing whether there's a -> or not.

        Personally, I find that $HASH{$key}->[$index] has a higher noise-to-signal ratio than $HASH{$key}[$index], so I prefer the latter.

Re: Help with references
by blokhead (Monsignor) on Oct 23, 2003 at 02:38 UTC
    $HASH{2}, for example, is an array reference. For any array reference, you can get a copy of the array by surrounding the reference by @{...}. You can get individual elements by putting ->[$index] after the reference. So..
    my @things = @{ $HASH{2} }; ## @things is now a copy of @ARRAY2 my $foo = $HASH{2}->[1]; ## $foo is now $ARRAY2[1]
    Also, when the -> dereferencing operator is in between subscripts (as it is here, between a hash and array subscript), it is optional. So the 2nd example would usually be written as $HASH{2}[1].

    blokhead

      I understand that blokhead included the syntax to copy array for completeness, but it sounds like you are new to Perl. So I think it is worth to tell you that, it is generally not a good idea to copy the entire array, as it hurts performance.

      To get hold of each individual array, you only need the array ref, which you can get by saying:

      $hash{1}