Reputation: 3289
There is a similar question How can I assign the result of a subroutine call to array references in Perl? but I'm curious about perl's possibilities
Is there a hack in perl to directly dereference element-wise an array of references?
in a code like
sub test { return([1..4],[5..8]); }
my (@a,@b);
my @result = test();
@a = @{$result[0]}; @b = @{$result[1]};
I would like to shorten the code to a simple statement like
sub test { return([1..4],[5..8]); }
my (\@a,\@b) = test();
or in a loop
foreach my $element (\"1",\"2",\"3") {
my $dereferenced_element = $$element;
it would be nice to write something like
foreach my \$element (\"1",\"2",\"3") {
I know that this syntax doesn't make much sense, as I don't want to assign a value to the reference of a variable, but to assign a dereferenced value to the variable itself
but I'm curious if there is anything in that direction in perl's repertoire and I think this example shows the best, what I'm intending to do
Upvotes: 3
Views: 2748
Reputation: 67900
The best way, IMO, is to assign the array refs to scalar variables, and dereference them as needed.
my ($x, $y) = test();
my @arrayx = @$x;
my @arrayy = @$y;
print "Element 1 in \$x is: $x->[1]\n";
for my $element (@$x) { ... }
You should also be aware that using $a
and $b
as variables is a bad idea, because they are predefined global variables used by the sort
routine. They can be used, like most predefined variables, but it may lead to strange behaviour and hard to find bugs.
Upvotes: 0
Reputation: 3037
@Qtax answer is neat. I was wondering else it could be done. Not exactly what you asked for, but near.
sub test { return [1..3], [2..4]; }
my (%a);
@a{'ret1','ret2'} = test();
print @{$a{'ret1'}} ;
print @{$a{'ret2'}} ;
Upvotes: 1
Reputation: 9436
This is not answering your question regarding the direct de-referencing but
what you are doing in:
sub test { return([1..4],[5..8]); }
my (@a,@b);
my @result = test();
@a = $result[0]; @b = $result[1];
is not entirely correct, your @a and @b arrays become 2d arrays after this.
Instead you should say:
@a = @{$result[0]};
@b = @{$result[1]};
or, as you most probably already know:
my ($a, $b) = test();
or:
for my $element (test()) {
# $element is an array ref
}
Upvotes: 2
Reputation: 33908
You can modify the globes directly if you want, but that is not a good practice.
sub test { return [1..3], [2..4]; }
(*x, *y) = test;
print "@x and @y";
Output:
1 2 3 and 2 3 4
This doesn't work with lexical (my
) variables. To make it work with strict
, you can declare the variables with our
(instead of my
).
Upvotes: 3