jreed21 jreed21 - 2 months ago 6
Perl Question

Why am I getting "Can't use string ("FormFields") as a HASH ref while "strict refs" in use" error

How would I fix this error? @names contains 'foo','bar'

my %PDFData = (
foo => (
FormFields => $FirstXML,
SignFields => $FirstXMLSign,
),
bar => (
FormFields => $SecondXML,
SignFields => $SecondXMLign,
),
);
my @names = @inputnames;
my $formfields;
my $signfields;
for my $i (0 .. $#names) {
$formfields .= $PDFData{ $names[$i] }{FormFields};
$signfields .= $PDFData{ $names[$i] }{SignFields};
};


Can't use string ("FormFields") as a HASH ref while "strict refs" in use at ./xmltest.pl line 263.

Answer

You're trying to assign a list to $foo and$bar (using parens in the assignments... parens represents a list) within the hash, where what you really want to assign are hash references.

In Perl, anything under the first level of a data structure must be a reference.

$bar => ( # <-- that parens denotes a list
    FormFields => $SecondXML,
    SignFields => $SecondXMLign,
) # <--

In the $foo and $bar assignments, change the parens I pointed out to braces: $foo => {...}, $bar => {...}, which represents an anonymous hash (reference).

The whole hash assignment should look like this:

my %PDFData = (
    $foo => {
        FormFields => $FirstXML,
        SignFields => $FirstXMLSign,
    },
    $bar => {
        FormFields => $SecondXML,
        SignFields => $SecondXMLign,
    },
);

If you were to desire arrays within the hash instead of hashes, you'd use brackets [ and ], which denotes an anonymous array (reference):

my %hash = (
    $foo => [
        1,
        2,
    ],
    $bar => [
        3,
        4,
    ],
);

Also, get to know Data::Dumper to help yourself get a visual as the first step to debugging/troubleshooting complex data structures. Here's an example of what you had (list) vs hash reference assignments:

use warnings;
use strict;

use Data::Dumper;

my %h = (
    first_level => (
        second_level => 1,
    ),
);

print Dumper \%h;

%h = (
    first_level => {
        second_level => 1,
    },
);

print Dumper \%h;

...and here's the difference in output:

# the list assignment output

$VAR1 = {
      '1' => undef,
      'first_level' => 'second_level'
    };

# the proper hash ref method output

$VAR1 = {
      'first_level' => {
                         'second_level' => 1
                       }
    };