2

This is the code:

my @items = (); # this is the array
my %x = {}; # the hash I'm going to put into the array
$x{'aa'} = 'bb'; # fill it up with one key-value pair
push(@items, $x); # add it to the array
my %i = @items[0]; # taking it back
print $i{'aa'}; # taking the value by the key

I expect it to print bb, but it doesn't print anything. What am I doing wrong?

1 Answer 1

6

What am I doing wrong?

Well, this doesn't do what you think:

my %x = {};

You can easily check:

use Data::Dumper;
print Dumper \%x;

The output:

Reference found where even-sized list expected at ./1.pl line 5.
$VAR1 = {
          'HASH(0x556a69fe8220)' => undef
        };

The first line comes from use warnings;. If you don't use it, start now.

Why is the contents of the hash so strange? The curly braces create a hash reference. As keys must be strings, the reference is stringified to the HASH(0xADDR). You don't want a reference, you want a list of keys and values.

my %x = ();

In fact, each hash and array starts up empty, so you don't have to use anything:

my @items;
my %x;

Or, you can populate it right ahead instead of doing it separately on the next line:

my %x = (aa => 'bb');

Similarly, this doesn't work:

push @items, $x;

It pushes value of the scalar variable $x into @items, but there's no such variable. It seems you aren't using use strict;. Start now, it will save you from similar errors.

You want to push the hash to the array, but array values are scalars - so you need to take a reference of the hash instead.

push @items, \%x;

No, you want to retrieve the hash from the array. Again, this doesn't work:

my %i = @items[0];

You are extracting a single value. Therefore, you shouldn't use @. Moreover, we now have a reference in the array, to populate a hash, we need to dereference it first:

my %i = %{ $items[0] };

And voilà, it works!

#!/usr/bin/perl
use warnings;
use strict;

my @items;               # this is the array
my %x;                   # the hash I'm going to put into the array
$x{aa} = 'bb';           # fill it up with one key-value pair
push @items, \%x;        # add it to the array
my %i = %{ $items[0] };  # taking it back
print $i{aa};            # taking the value by the key
Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.