Beefy Boxes and Bandwidth Generously Provided by pair Networks
laziness, impatience, and hubris
 
PerlMonks  

I don't understand hash references

by monk2b (Pilgrim)
on Dec 07, 2009 at 15:14 UTC ( #811514=perlquestion: print w/replies, xml ) Need Help??

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

I understand hashes fine. I now know I don't under hash references because after a day of playing with hash references I still can not get to all of my data. I am initializing my refernce in a loop like this.
$hashr->{$name}->{$id}->{$comment}
I then attempt to get to the data in the reference like this
for $k1 ( sort keys %$hashr ) { print "$k1\n"; for $k2 (sort keys %{$hashr->{ $k1 }} ) { $k3 = %{$hashr->{ $k1 }->{ $k2 }}; print "$k2\t\t$k3\n"; } }
I am able to get the $k1 data, I am able to get the $k2 data. I am not able to get the $k3 information. I wonder if I am really adding the comment to the this hash reference.
Perl Good - Manual process bad

Replies are listed 'Best First'.
Re: I don't understand hash references
by LanX (Sage) on Dec 07, 2009 at 15:28 UTC
    $k3 = %{$hashr->{ $k1 }->{ $k2 }};

    is analogues to

    $k=%hash

    $k3 is not a hashref but the scalar-value of a hash (... which produces something mostly useless like 1/8 indicating the memory use)

    what you really want is either

    $k3 = $hashr->{ $k1 }->{ $k2 };

    to get the hashref

    or

    %h3 = %{$hashr->{ $k1 }->{ $k2 }};

    to copy the nested sub-hash!

    Cheers Rolf

Re: I don't understand hash references
by biohisham (Priest) on Dec 07, 2009 at 16:29 UTC

    You have used the $comment as a key in the hash and not the value to be assigned to the hash ... I will show an example at the bottom, probably taking a retrospective look can prove beneficial ...

    using the module Data::Dumper can allow you to view the data structure representation and understand or decide how to approach it since it makes that data structure stringified...

    The Data Structure Cookbook is fantastic, I hope you have consulted it and that you can revert to it over and over, it is so useful...

    I found Referencing in advanced data structures a very good source of clearing my confusion regarding many things...They seem difficult to understand but once you practiced them enough and you would find yourself starting to make sense of it all.. Also, Check the Tutorials section, for many related things have been graciously contributed by the beloved monks....

    in the code example, notice the two lines:

    $hash{$name}{$id}= $comment; push @{$hash{$name}{$id}}, $comment; #this one has been commented out

    my %hash; my ($name, $id, $comment); while(<DATA>){ chomp; my ($name, $id, $comment)=split; $hash{$name}{$id}= $comment; #adding comment to + related $name/$id.. #push @{$hash{$name}{$id}}, $comment; #create an anonymo +us array #in case more than + one $comment or other variables related to same $name/$id }
    In case your DATA looked like:
    Name1 12 firstname1 some more info

    The name, the ID and then followed by more than one item to be associated with $name,$id, you would configure your split to break properly and then treat $hash{$name}{$id} as an anonymous array reference that would accept qw(some more info), using push or other array manipulation techniques...

    Iterating is done with respect to the type of reference and it's location within the structure, the function ref or the Data::Dumper output can be handy at this time

    for my $key1(sort keys %hash){ print "$key1\t->$hash{$key1}\t"; #$hash{$key} hash referenc +e,to access it dereference it..... foreach $key2(sort keys %{$hash{$key1}}){ print "$key2\t->$hash{$key1}{$key2}\t\n"; } }

    I hope this has been as concise and worthy for you to get to grabs, I haven't mentioned about iterating through @{$hash{$name}{$id}} for my confidence that you would figure it out. Let us know if you get any confusion...this is the entire code example

    use strict; use warnings; my %hash; my ($name, $id, $comment); while(<DATA>){ chomp; my ($name, $id, $comment)=split; $hash{$name}{$id}= $comment; #push @{$hash{$name}{$id}}, $comment; } print "Key\t\t Val\t\t Key\t Val\n"; print "---------------------------------------------------\n"; for my $key1(sort keys %hash){ print "$key1\t->$hash{$key1}\t"; foreach my $key2(sort keys %{$hash{$key1}}){ print "$key2\t->$hash{$key1}{$key2}\t\n"; } } use Data::Dumper; print Dumper(\%hash); __DATA__ Name1 12 firstname1 Name2 55 firstname2 Name3 20 firstname3
    Have an enjoyable Perl journey...


    Excellence is an Endeavor of Persistence. Chance Favors a Prepared Mind.
Re: I don't understand hash references
by JavaFan (Canon) on Dec 07, 2009 at 15:17 UTC
Re: I don't understand hash references
by kyle (Abbot) on Dec 07, 2009 at 15:35 UTC
Re: I don't understand hash references
by planetscape (Chancellor) on Dec 08, 2009 at 01:26 UTC
Re: I don't understand hash references
by monk2b (Pilgrim) on Dec 07, 2009 at 17:40 UTC
    Thanks you all,

    biohisham,

    Very nice and understandable tutorial, thank you very much and believe me, I got it now.


    Perl Good - Manual process bad

Log In?
Username:
Password:

What's my password?
Create A New User
Domain Nodelet?
Node Status?
node history
Node Type: perlquestion [id://811514]
Approved by Corion
Front-paged by biohisham
help
Chatterbox?
and the web crawler heard nothing...

How do I use this? | Other CB clients
Other Users?
Others avoiding work at the Monastery: (2)
As of 2021-09-22 04:54 GMT
Sections?
Information?
Find Nodes?
Leftovers?
    Voting Booth?

    No recent polls found

    Notices?