When I using following code, subroutine f can't print @_ correctly for the substitution of $tmp before it, which is explainable.
use strict;
use warnings;
sub f {
# print("args = ", @_);
my $tmp = "111";
$tmp =~ s/\d+//;
print("args = ", @_);
}
"dd11ddd" =~ /(?<var>\d+)/;
f($+{"var"});
But when I uncomment the first print statement, then both print could give the correct @_, which makes me confused, why the capture group hasn't been overwrite. Or just some underlay mechanism of perl I don't know? Please help, thanks.
When I pass capture group into perl subroutine, the capture group hasn't been overwritten as expected. I want to know why this could happen and how to explain it correctly.
Perl arguments are passed by reference.
sub f {
$_[0] = "def";
}
my $x = "abc;
say $x; # abc
f( $x );
say $x; # def
%+ is affected by $tmp =~ s/\d+//, and thus so is $_[0]. We don't usually run into problems because we usually make an explicit copy of the arguments.
sub f {
my $y = shift;
$y = "def";
}
my $x = "abc";
say $x; # abc
f( $x );
say $x; # abc
Passing a copy of the scalar would also avoid the problems.
sub f {
$_[0] = "def";
}
my $x = "abc";
say $x; # abc
f( "$x" );
say $x; # abc
The above explains why you get weird behaviour and how to avoid it, but not why accessing $_[0] before the substitution seems to fix it. Honestly, it doesn't really matter. It's some weird interaction between the magical nature of %+, the implicit localization of %+, the optimizations to avoid needless implication localizations of %+, and the way localization works.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With