I have Hash where values of keys are other Hashes.
Example: {'key' => {'key2' => {'key3' => 'value'}}}
How can I iterate through this structure?
Loop over Perl hash values Perl allows to Loop over its Hash values. It means the hash is iterative type and one can iterate over its keys and values using 'for' loop and 'while' loop. In Perl, hash data structure is provided by the keys() function similar to the one present in Python programming language.
Perl for Beginners: Learn A to Z of Perl Scripting Hands-on A hash is a set of key/value pairs. Hash variables are preceded by a percent (%) sign. To refer to a single element of a hash, you will use the hash variable name preceded by a "$" sign and followed by the "key" associated with the value in curly brackets..
Extracting Keys and Values from a Hash variable The list of all the keys from a hash is provided by the keys function, in the syntax: keys %hashname . The list of all the values from a hash is provided by the values function, in the syntax: values %hashname . Both the keys and values function return an array.
To add another hash to an array, we first initialize the array with our data. Then, we use push to push the new hash to the array. The new hash should have all of its data. As shown below, you can see the difference between the two arrays before and after pushing a new hash.
This answer builds on the idea behind Dave Hinton's -- namely, to write a general purpose subroutine to walk a hash structure. Such a hash walker takes a code reference and simply calls that code for each leaf node in the hash.
With such an approach, the same hash walker can be used to do many things, depending on which callback we give it. For even more flexibility, you would need to pass two callbacks -- one to invoke when the value is a hash reference and the other to invoke when it is an ordinary scalar value. Strategies like this are explored in greater depth in Marc Jason Dominus' excellent book, Higher Order Perl.
use strict;
use warnings;
sub hash_walk {
my ($hash, $key_list, $callback) = @_;
while (my ($k, $v) = each %$hash) {
# Keep track of the hierarchy of keys, in case
# our callback needs it.
push @$key_list, $k;
if (ref($v) eq 'HASH') {
# Recurse.
hash_walk($v, $key_list, $callback);
}
else {
# Otherwise, invoke our callback, passing it
# the current key and value, along with the
# full parentage of that key.
$callback->($k, $v, $key_list);
}
pop @$key_list;
}
}
my %data = (
a => {
ab => 1,
ac => 2,
ad => {
ada => 3,
adb => 4,
adc => {
adca => 5,
adcb => 6,
},
},
},
b => 7,
c => {
ca => 8,
cb => {
cba => 9,
cbb => 10,
},
},
);
sub print_keys_and_value {
my ($k, $v, $key_list) = @_;
printf "k = %-8s v = %-4s key_list = [%s]\n", $k, $v, "@$key_list";
}
hash_walk(\%data, [], \&print_keys_and_value);
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With