问题
The top answer in this post: How can I create a multidimensional array in Perl? suggests building a multi-dimensional array as follows:
my @array = ();
foreach my $i ( 0 .. 10 ) {
foreach my $j ( 0 .. 10 ) {
push @{ $array[$i] }, $j;
}
}
I am wondering if there is a way of building the array more compactly and avoiding the nested loop, e.g. using something like:
my @array = ();
my @other_array = (0 ... 10);
foreach my $i ( 0 .. 10 ) {
$array[$i] = @other_array; # This does not work in Perl
}
}
Does Perl support any syntax like that for building multi-dimensional arrays without nested looping?
Similarly, is there a way to print the multidimensional array without (nested) looping?
回答1:
There is more than one way to do it:
Generating
push accepts LISTs
my @array;
push @{$array[$_]}, 0 .. 10 for 0 .. 10;
Alternative syntax:
my @array;
push @array, [ 0 .. 10 ] for 0 .. 10;
map eye-candy
my @array = map { [ 0 .. 10 ] } 0 .. 10;
Alternative syntax:
my @array = map [ 0 .. 10 ], 0 .. 10;
Printing
With minimal looping
print "@$_\n" for @array;
On Perl 5.10+
use feature 'say';
say "@$_" for @array;
With more formatting control
print join( ', ', @$_ ), "\n" for @array; # "0, 1, 2, ... 9, 10"
"No loops" (The loop is hidden from you)
use Data::Dump 'dd';
dd @array;
Data::Dumper
use Data::Dumper;
print Dumper \@array;
Have a look at perldoc perllol for more details
回答2:
You are close, you need a reference to the other array
my @array; # don't need the empty list
my @other_array = (0 ... 10);
foreach my $i ( 0 .. 10 ) {
$array[$i] = \@other_array;
# or without a connection to the original
$array[$i] = [ @other_array ];
# or for a slice
$array[$i] = [ @other_array[1..$#other_array] ];
}
}
You can also make anonymous (unnamed) array reference directly using square braces [] around a list.
my @array;
foreach my $i ( 0 .. 10 ) {
$array[$i] = [0..10];
}
}
Edit: printing is probably easiest using the postfix for
print "@$_\n" for @array;
for numerical multidimensional arrays, you can use PDL. It has several constructors for different use cases. The one analogous to the above would be xvals. Note that PDL objects overload printing, so you can just print them out.
use PDL;
my $pdl = xvals(11, 11);
print $pdl;
来源:https://stackoverflow.com/questions/12392127/building-and-printing-a-multidimensional-list-in-perl-without-looping