Login

Perl: Another Round with Hashes

Welcome to the eighth episode in our series on Perl Lists and Hashes. In this article we will discuss how to add a record to a hash, as well as how to remove a record from one. We will also cover how to check to see if a record already exists in our hash, how to write the data contained in one to a file, and quite possibly go over the basics of multidimensional lists.

In our previous issue we learned the basics of hashes — such as how to create them, print individual values from them and print only the value. We also learned a way to print the keys. Additionally, we worked with some alternative methods to create hashes and assign values to them, such as using the => operator and using other hashes as their foundation. While we were at it, we learned to create variables and lists out of the elements within a hash.

Want Some Hash with that Shake?

Adding a value to a hash that already exists is similar to adding a value to a previously created list. In the following example, we begin by creating a hash name %Wrestler that will hold two key-value pairs, representing the Champ, CM Punk, and the Chump, Chavo Guerrero. We will then add a third value, ‘The Miz’, with the key, Dumb. Here it is in code:

#!/usr/bin/perl

%Wrestlers=(Champ=> ‘ CM Punk ‘, Chump => ‘ Chavo Guerrero ‘);

print values(%Wrestlers);

print "nn";

$Wrestlers{Dumb}=’ The Miz ‘;

print values(%Wrestlers);

When we run this program, we get the following result:

CM Punk Chavo Guerrero

CM Punk The Miz Chavo Guerrero

Since we are only adding one value and key, we used the $Wrestlers variable and enclosed our key in curly braces {Dumb}. We then told the program to assign the value ‘The Miz’ to the key and assigned the $Wrestlers variable to our hash. Note that the name $Wrestlers matches the name of the hash, %Wrestlers. If they differ, this program will not work as we intended.

We can also add a value to a hash by using a variable. Let’s say we have a variable that holds the name of a wrestler. Here is how we add him to the %Wrestler hash:

#!/usr/bin/perl

%Wrestlers=(Champ=> ‘ CM Punk ‘, Chump => ‘ Chavo Guerrero ‘);

$New="Big John Stud";

print values(%Wrestlers);

print "nn";

$Wrestlers{OldSkool}=$New;

print values(%Wrestlers);

Note that we had to assign a key for our variable (OldSkool). Without this, the code would not have worked properly, as Perl would not have known how to reference Big John Stud.

This program gives us the result:

CM Punk Chavo Guerrero

Big John Stud CM Punk Chavo Guerrero

If you want to see how the keys to verify that the new additions were stored properly, you can do so like this:

#!/usr/bin/perl

%Wrestlers=(Champ, ‘ CM Punk ‘, Chump, ‘ Chavo Guerrero ‘);

$New="Big John Stud";

print values(%Wrestlers);

print "nn";

$Wrestlers{OldSkool}=$New;

@All = keys(%Wrestlers);

foreach $Stuff(@All)

{print "The key for $Wrestlers{$Stuff} is $Stuffn"};

Giving us the result:

The key for Big John Stud is OldSkool

The key for CM Punk is Champ

The key for Chavo Guerrero is Chump

{mospagebreak title=Adding More Than One Record}

There are several ways to add multiple records to a hash. Here, we are going to add Brutus “the Barber” Beefcake to our already created hash:

#!/usr/bin/perl

%Wrestlers=(Champ=> ‘ CM Punk ‘, Chump => ‘ Chavo Guerrero ‘);

$New=" Big John Stud ";

$Boof=" Brutus Beefcake ";

print values(%Wrestlers);

print "nn";

$Wrestlers{OldSkool}=$New;

$Wrestlers{Beef}=$Boof;

print values(%Wrestlers);

Note that each time, $Wrestlers holds our values. When we print this code we get the following result:

Brutus Beefcake Big John Stud CM Punk Chavo Guerrero

Replacing a Record in a Hash

Replacing a record in a hash with another record is pretty similar to adding a record. In our previous examples we stated that CM Punk was the champ (well we assigned his value to the champ key at any rate). But what happens if CM dies in a horrible car accident and the title is given to someone else? Here is how we would replace the value in the key ‘champ':

#!/usr/bin/perl

%Wrestlers=(Champ=> ‘ CM Punk ‘, Chump => ‘ Chavo Guerrero ‘,

OldSkool=> ‘ Big John Stud ‘, Boof=> ‘ Brutus Beefcake ‘);

$New=" The Nature Boy Ric Flair ";

print values(%Wrestlers);

print "nn";

$Wrestlers{Champ}=$New;

print values(%Wrestlers);

Here, the %Wrestlers hash has been created and assigned a bunch of key-pair values. Next, we create a variable named $New to hold a given value. Next we print out the values of our %Wrestlers hash, then assign the key “Champ” a new value, said value being the one stored in $New. Finally, we print out the value of %Wrestlers once more to confirm that the replace took place.

This works because Perl sees the “Champ” key and searches in the hash for it. If it finds it, it replaces its value with the one you specify. If not, it adds it to the hash.

You can achieve the same without variables of course:

#!/usr/bin/perl

%Wrestlers=(Champ=> ‘ CM Punk ‘, Chump => ‘ Chavo Guerrero ‘,

OldSkool=> ‘ Big John Stud ‘, Boof=> ‘ Brutus Beefcake ‘);

print values(%Wrestlers);

print "nn";

$Wrestlers{Champ}="The Nature Boy Ric Flair";

print values(%Wrestlers);

Giving us the same result as above:

Brutus Beefcake Big John Stud CM Punk Chavo Guerrero

Brutus Beefcake Big John Stud The Nature Boy Ric Flair Chavo Guerrero

{mospagebreak title=Using the Delete Function}

But what if we don’t want to replace CM Punk just yet? Perhaps they are going to decide the new champ via a Wrestlemania contest or something. In this case, we may wish to delete the record for now and add it later. Deleting a record in a hash is a simple matter. To do so, we simply use the conveniently built-in delete() function:

#!/usr/bin/perl

%Wrestlers=(Champ=> ‘ CM Punk ‘, Chump => ‘ Chavo Guerrero ‘,

OldSkool=> ‘ Big John Stud ‘, Boof=> ‘ Brutus Beefcake ‘);

print values(%Wrestlers);

print "nn";

delete($Wrestlers{Champ});

print values(%Wrestlers);

Here, once more values are assigned to a hash and printed out. Then we use delete() to remove a record by specifying which record to remove. In this instance we removed the value in “Champ.” When we print this out, we get the following result:

Brutus Beefcake Big John Stud CM Punk Chavo Guerrero

Brutus Beefcake Big John Stud Chavo Guerrero

Now let’s say that CM Punk and Chavo Guerrero happened to be riding in the same car and both of them died. If we wanted to delete multiple records from our hash, we could do so in the following manner:

#!/usr/bin/perl

%Wrestlers=(Champ=> ‘ CM Punk ‘, Chump => ‘ Chavo Guerrero ‘,

OldSkool=> ‘ Big John Stud ‘, Boof=> ‘ Brutus Beefcake ‘);

print values(%Wrestlers);

print "nn";

delete(@Wrestlers{Champ,Chump});

print values(%Wrestlers);

As you can see, this is very similar code. The only differences really are the addition of the record Chump, separated by a comma, and the change of the variable $Wrestlers to a list, or @Wrestlers, since we are removing more than one record.

Here are our results:

Brutus Beefcake Big John Stud CM Punk Chavo Guerrero

Brutus Beefcake Big John Stud

The wrestling world sure is shrinking.

{mospagebreak title=Storing a Deleted Value in a Variable}

We don’t have to simply do away with our deleted value. In the following code, we will store it in a variable and append it to a sentence:

#!/usr/bin/perl

%Wrestlers=(Champ=> ‘ CM Punk ‘, Chump => ‘ Chavo Guerrero ‘,

OldSkool=> ‘ Big John Stud ‘, Boof=> ‘ Brutus Beefcake ‘);

print values(%Wrestlers);

print "nn";

$Dead=delete(@Wrestlers{Champ});

print values(%Wrestlers);

print "nn";

print "This guy is dead: " . $Dead;

Here we have:

Brutus Beefcake Big John Stud CM Punk Chavo Guerrero

Brutus Beefcake Big John Stud Chavo Guerrero

This guy is dead: CM Punk

And finally, we come back to our scenario where both Chavo and CM Punk die. Now we would like to add them to a growing list of dying wrestlers. Since seeing is believing, here is the eye-catching code:

#!/usr/bin/perl

%Wrestlers=(Champ=> ‘ CM Punk ‘, Chump => ‘ Chavo Guerrero ‘,

OldSkool=> ‘ Big John Stud ‘, Boof=> ‘ Brutus Beefcake ‘);

print values(%Wrestlers);

print "nn";

@Dead=delete(@Wrestlers{Champ,Chump});

print values(%Wrestlers);

print "nn";

print "These guys are dead: " . @Dead[0] . @Dead[1];

This will delete the records for ‘Champ’ and ‘Chump’ and store them in the list @Dead. When we run this program we get the following printout:

Brutus Beefcake Big John Stud CM Punk Chavo Guerrero

Brutus Beefcake Big John Stud

These guys are dead: CM Punk Chavo Guerrero

One final note. Had you tried to write out both values in the @Dead list like so:

print "These guys are dead: " . @Dead;

You would have been given the sentence:

These guys are dead: 2

Instead of printing the values, it would have printed the number of elements. Why that is, I am not certain.

Well that’s all the time we have for this one. Be sure to stop by next time as we continue talking about hashes and go into those multidimensional lists you’ve been hearing so much about.