5.9.3. Discussion
This technique uses the list equivalence of hashes mentioned in the
introduction. In list context, reverse treats
%LOOKUP as a list and reverses the order of its
elements. The significant property of a hash treated as a list is
that the list elements come in associated pairs: the first element is
the key; the second, the value. When you reverse
such a list, the first element is now the value, and the second the
key. Treating this list as a hash results in a
hash whose values are the keys of the original hash and vice versa.
Here's an example:
%surname = ( "Mickey" => "Mantle", "Babe" => "Ruth" );
%first_name = reverse %surname;
print $first_name{"Mantle"}, "\n";
Mickey
When we treat %surname as a list, it becomes:
("Mickey", "Mantle", "Babe", "Ruth")
(or maybe ("Babe", "Ruth",
"Mickey", "Mantle") because we
can't predict the order). Reversing this list gives us:
("Ruth", "Babe", "Mantle", "Mickey")
When we treat this list as a hash, it becomes:
("Ruth" => "Babe", "Mantle" => "Mickey")
Now instead of turning first names into surnames, it turns surnames
into first names.
If any values in the original hash were references instead of strings
or numbers, the inverted hash poses a problem because references
don't work well as hash keys—unless you use the Tie::RefHash
module described in Recipe 5.13.