Just so you'll know what not to do, here's what you asked for in the OP:
c:\@Work\Perl\monks>perl -wMstrict -MData::Dump -le
"our @A_0;
our @A_1;
our @A_2;
our @A_3;
;;
for my $i (0 .. 3) {
my $name = qq{A_$i};
no strict 'refs';
$name->[$i] = 1000 + $i;
}
dd \@A_0;
dd \@A_1;
dd \@A_2;
dd \@A_3;
"
[1000]
[undef, 1001]
[undef, undef, 1002]
[undef, undef, undef, 1003]
This works with strict (and warnings) fully enabled, but only by invoking no strict 'refs' just before things go sideways. This | Soft referencing only works with package global variables, one of the drawbacks of soft referencing. In the example, our is used to declare the package global arrays. Note that the
my $name = qq{A_$i};
statement could be eliminated and the reference could be taken directly from the constructed string:
qq{A_$i}->[$i] = 1000 + $i;
(I use Data::Dump::dd() because I like it, but it's not core. Data::Dumper is core.)
Much better practice is the use of hard references:
c:\@Work\Perl\monks>perl -wMstrict -MData::Dump -le
"my @A_0;
my @A_1;
my @A_2;
my @A_3;
;;
for my $arrayref ( \(@A_0, @A_1, @A_2, @A_3) ) {
$arrayref->[0] = 1234;
}
dd \@A_0;
dd \@A_1;
dd \@A_2;
dd \@A_3;
"
[1234]
[1234]
[1234]
[1234]
Note that the variables being operated on are my (or lexical) variables, but the same referencing mechanism works with package globals (our variables) as well. Note also the \(@ra, @rb, ...) syntax for taking hard references to a collection of (any mixture of) variables. This is just a convenience, and the loop could just as well have been defined
for my $arrayref (\@A_0, \@A_1, \@A_2, \@A_3) { ... }
The \( ... ) device can be used in conjunction with the declaration of a set of variables and the list of references taken can be captured in an array. The set of references in this array can then be operated on as a group. Note that the \my ( ... ) device can be used only to declare and not to initialize variables. The lexical variables created in the my (@A_0, @foo, @A_2, @A_3) expression below behave just like any lexical; they could also be our variables.
c:\@Work\Perl\monks>perl -wMstrict -MData::Dump -le
"my @arrayrefs = ( \my (@A_0, @foo, @A_2, @A_3) );
;;
for my $i (0 .. $#arrayrefs) {
$arrayrefs[$i][$i] = 1000 + $i;
}
dd \@A_0;
dd \@foo;
dd \@A_2;
dd \@A_3;
"
[1000]
[undef, 1001]
[undef, undef, 1002]
[undef, undef, undef, 1003]
(Update: The
my @arrayrefs = ( \my (@A_0, @foo, @A_2, @A_3) );
statement could be written slightly more simply as
my @arrayrefs = \my (@A_0, @foo, @A_2, @A_3);
since the outermost ( ) grouping is unnecessary.)
A reference to the @arrayrefs array could be taken and passed around, etc., etc. Use your imagination — but don't use soft references (without a very good reason, but you didn't hear me say that).
Update: And here's yet another variation that uses each to simultaneously iterate over the indices and elements of the @arrayrefs array (needs Perl version 5.12+):
c:\@Work\Perl>perl -wMstrict -MData::Dump -le
"use 5.012;
;;
my @arrayrefs = \my (@A_0, @foo, @A_2, @A_3);
;;
while (my ($i, $ar) = each @arrayrefs) {
$ar->[$i] = 1000 + $i;
}
dd \@A_0;
dd \@foo;
dd \@A_2;
dd \@A_3;
"
[1000]
[undef, 1001]
[undef, undef, 1002]
[undef, undef, undef, 1003]
Give a man a fish: <%-{-{-{-<
|