import-bot (20211) [Avatar] Offline
#1
[Originally posted by fjohn]

Hello Andrew,
I have encountered this nested anonymous hash data structure and was
wondering if you could clarify its meaning. These anonymous data structures
keep tripping me up, particularly hashes. I referred to your book, but
couldn't locate something similar. Thanks.
$hash{toes} = {
biggest => 'hairy troll',
smallest => 'toddler',
};
import-bot (20211) [Avatar] Offline
#2
Re: Hash references
[Originally posted by jandrew]

Fred,

OK, the structure is:

$hash{toes} = {
biggest => 'hairy troll',
smallest => 'toddler',
};

Let's start at the inside. We can construct an anonymous hash with
curly braces --- and an anonymous hash is a reference so we can
store it in an ordinary scalar variable:

my $hashref = { biggest => "hairy troll",
smallest => "toddler",
};

We have a reference to a hash containing two key/value pairs, and
we can access these by dereferencing:


print "$hashref->{biggest}
"; # prints: hairy troll
print "$hashref->{smallest}
"; # prints: toddler

Now let's consider the outer hash. We can assign any legal scalar
value as the value of key in a hash:

my %hash;
$hash{number} = 42; # assign a number
$hash{string} = "foo"; # assign a string

And because a reference is a legal scalar value:

my @array = (1,2,3);

$hash{aref} = @array; # assign a ref to an array
$hash{aaref} = [1,2,3]; # assign a ref to an anonymous array

So, in the structure you gave we are just assigning a reference to an
anonymous hash as the value of a particular key in the hash:

my %hash;
$hash{toes} = {
biggest => 'hairy troll',
smallest => 'toddler',
};

At this point we have a hash named %hash that holds one key/value
pair: the key is "toes" and the value is a reference to an anonymous
hash (which itself holds two key/value pairs).

In this example, if we want to print out the value of one of the
inner keys (say, "biggest") we can do:

print $hash{toes}->{biggest}, "
";

We are dereferencing just as we did when we printed out values from
$hashref earlier in this post. However, we do not actually need the
dereference arrow in this case because it is always assumed between
any two subscripts --- so we can also just say:

print $hash{toes}{biggest}, "
";


This is not unlike the slightly larger example shown on page 149
using the %employees hash. It might be more apparent if we show your
hash like:

my %hash = ( toes => { biggest => 'hairy troll',
smallest => 'toddler',
},
);


And we could have used more first level keys:

my %hash = ( toes => { biggest => 'hairy troll',
smallest => 'toddler',
},
ears => { biggest => 'elf',
smallest => 'hobbit'
);

Which would be the same as if we did:

my %hash;
$hash{toes} = {
biggest => 'hairy troll',
smallest => 'toddler',
};
$hash{ears} = {
biggest => 'elf',
smallest => 'hobbit',
};

And we could iterate through the keys and print values just as we do
for the %employees hash on page 149.

I hope this helps clarify things to some extent --- if not, don't
hesitate to ask further.

regards,
andrew
import-bot (20211) [Avatar] Offline
#3
Re: Hash references
[Originally posted by fjohn]

> Fred,
>
> OK, the structure is:
>
> $hash{toes} = {
> biggest => 'hairy troll',
> smallest => 'toddler',
> };
>
> Let's start at the inside. We can construct an anonymous hash with
> curly braces --- and an anonymous hash is a reference so we can
> store it in an ordinary scalar variable:
>
> my $hashref = { biggest => "hairy troll",
> smallest => "toddler",
> };
>
> We have a reference to a hash containing two key/value pairs, and
> we can access these by dereferencing:
>
>
> print "$hashref->{biggest}
"; # prints: hairy troll
> print "$hashref->{smallest}
"; # prints: toddler
>
> Now let's consider the outer hash. We can assign any legal scalar
> value as the value of key in a hash:
>
> my %hash;
> $hash{number} = 42; # assign a number
> $hash{string} = "foo"; # assign a string
>
> And because a reference is a legal scalar value:
>
> my @array = (1,2,3);
>
> $hash{aref} = @array; # assign a ref to an array
> $hash{aaref} = [1,2,3]; # assign a ref to an anonymous array
>
> So, in the structure you gave we are just assigning a reference to an
> anonymous hash as the value of a particular key in the hash:
>
> my %hash;
> $hash{toes} = {
> biggest => 'hairy troll',
> smallest => 'toddler',
> };
>
> At this point we have a hash named %hash that holds one key/value
> pair: the key is "toes" and the value is a reference to an anonymous
> hash (which itself holds two key/value pairs).
>
> In this example, if we want to print out the value of one of the
> inner keys (say, "biggest"smilie we can do:
>
> print $hash{toes}->{biggest}, "
";
>
> We are dereferencing just as we did when we printed out values from
> $hashref earlier in this post. However, we do not actually need the
> dereference arrow in this case because it is always assumed between
> any two subscripts --- so we can also just say:
>
> print $hash{toes}{biggest}, "
";
>
>
> This is not unlike the slightly larger example shown on page 149
> using the %employees hash. It might be more apparent if we show your
> hash like:
>
> my %hash = ( toes => { biggest => 'hairy troll',
> smallest => 'toddler',
> },
> );
>
>
> And we could have used more first level keys:
>
> my %hash = ( toes => { biggest => 'hairy troll',
> smallest => 'toddler',
> },
> ears => { biggest => 'elf',
> smallest => 'hobbit'
> );
>
> Which would be the same as if we did:
>
> my %hash;
> $hash{toes} = {
> biggest => 'hairy troll',
> smallest => 'toddler',
> };
> $hash{ears} = {
> biggest => 'elf',
> smallest => 'hobbit',
> };
>
> And we could iterate through the keys and print values just as we do
> for the %employees hash on page 149.
>
> I hope this helps clarify things to some extent --- if not, don't
> hesitate to ask further.
>
> regards,
> andrew

So in the last example as I understand it, 'toes' is a key whose value is an
anonymous hash, with one of its keys being 'biggest' and its value is hairy
troll? I think I got it.
Do you know of any good resources that provide more descriptions and examples
of nested data stuctures. It seems like there are so many different ways to
create nested hashes that I am always encountering a method that I have not
seen before. It could be my inexperience with them, but whenever I think I
have a good understanding of, up pops a method that I have not seen.
import-bot (20211) [Avatar] Offline
#4
Re: Hash references
[Originally posted by jandrew]

Yes it looks like you have it smilie

As for other resources, well, there are the standard docs on
references and datastructures:

perldoc perlreftut
perldoc perlref
perldoc perllol
perldoc perldsc

And you may also peruse my April 2001 series of short articles
on references:

http://members.shaw.ca/andrew-johnson/perl/archit/Apr01

You might also consider visiting (and becoming a member of) the
perlmonks forum/community, which does have tutorial section
(including a couple of small reference tutorials). More importantly,
it is an active community of Perl people of all skill levels asking
and answering questions and discussing various Perl and programming
related topics, and is somewhat friendlier than the newsgroups. More
people means more points of view and more examples. Much can be
learned just lurking, even more by participation. Check out:

http://www.perlmonks.org/


regards,
andrew