Как поместить массив хэшей в массив хэшей? - PullRequest
1 голос
/ 23 февраля 2011

У меня есть этот скрипт

#!/usr/bin/perl

use warnings;
use strict;

use Data::Dumper;

my %acc = ();

&insert_a(\%acc, 11);
&insert_p(\%acc, 111);
print Dumper %acc;

sub insert_a() {

    my $acc_ref = shift;

    $acc_ref->{"$_[0]"} = {
    a => -1,
    b => -1,
    c => [ { }, ],
    }
}

sub insert_p() {

    my $acc_ref = shift;

    my @AoH = (
    {
        d => -1,
        e => -1,
    }
    );

    push $acc_ref->{"$_[0]"}{"c"}, @AoH;
}

, где я пытаюсь вставить AoH в c, который также является AoH, но я получаю

Type of arg 1 to push must be array (not hash element) at ./push.pl line 36, near "@AoH;"
Execution of ./push.pl aborted due to compilation errors.

Есть идеи, как это сделать?

Ответы [ 3 ]

2 голосов
/ 23 февраля 2011

Конкретная проблема заключается в том, что вы можете передать только массив, поэтому сначала нужно разыменовать массив, а затем, поскольку он находится в более крупной структуре данных, вы хотите установить его значение в качестве ссылки.

#!/usr/bin/perl

use warnings;
use strict;

use Data::Dumper;

my %acc = ();

# don't use & to call subs; that overrides prototypes (among other things)
# which you won't need to worry about, because you shouldn't be using
# prototypes here; they're used for something else in Perl.
insert_a(\%acc, 11);
insert_p(\%acc, 111);
# use \%acc to print as a nice-looking hashref, all in one variable
print Dumper \%acc;

# don't use () here - that's a prototype, and they're used for other things.
sub insert_a {

    my $acc_ref = shift;

    $acc_ref->{"$_[0]"} = {
    a => -1,
    b => -1,
    c => [ { }, ],
    }
}

# same here
sub insert_p {

    my $acc_ref = shift;

    my @AoH = (
      {
        d => -1,
        e => -1,
      }
    );

    # You need to dereference the first array, and pass it a reference
    # as the second argument.
    push @{ $acc_ref->{"$_[0]"}{"c"} }, \@AoH;
}

Я не совсем уверен, что полученная структура данных соответствует вашим ожиданиям, но теперь, когда программа работает и вы можете видеть полученную структуру, вы можете изменить ее, чтобы получить то, что вам нужно.

1 голос
/ 23 февраля 2011

Хеш-значения всегда скалярны, поэтому для хранения массива в хеш-памяти вам необходимо сохранить ссылку на массив.Попробуйте использовать следующую строку, где значение хеша разыменовывается в массив.

push @{ $acc_ref->{$_[0]}->{'c'} }, @AoH;
1 голос
/ 23 февраля 2011

Делай как,

push @{$acc_ref->{"$_[0]"}->{"c"}}, @AoH;

или вы можете попробовать $acc_ref->{"$_[0]"}->{"c"} = \@AoH;

Ваш сценарий,

use strict;
use warnings
use Data::Dumper;

my %acc = ();

&insert_a(\%acc, 11);
&insert_p(\%acc, 111);
print Dumper %acc;

sub insert_a() {

    my $acc_ref = shift;

    $acc_ref->{"$_[0]"} = {
    a => -1,
    b => -1,
    c => [ { }, ],
    }
}

sub insert_p() {

    my $acc_ref = shift;

    my @AoH = (
    {
        d => -1,
        e => -1,
    }
    );

    push @{$acc_ref->{"$_[0]"}->{"c"}}, @AoH;
}

Выход:

$VAR1 = '11';
$VAR2 = {
          'c' => [
                   {}
                 ],
          'a' => -1,
          'b' => -1
        };
$VAR3 = '111';
$VAR4 = {
          'c' => [
                   {
                     'e' => -1,
                     'd' => -1
                   }
                 ]
        };
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...