Matija said:
X-Ftn-To: Paul Lalli
Paul Lalli said:
If you want to change the argument to f(), change it directly:
$_[0] = 5;
Yes, no doubt about that, but I think that I've read somewhere how shift
keeps the "magic" when operating on @_.
Well, since your expected results clearly do not mesh with reality, it
would seem that either 1) What you read was incorrect, or 2) You are
misremembering or misunderstanding what you read. If you manage to
find the citation you're talking about, please feel free to post it
here for our examination...
btw, Bart showed something interesting,
perl -le "sub f { $_=5 for shift } f(my $b=1); print $b"
should be doing the same thing as,
perl -le "sub f { $_=5 for map $_, shift } f(my $b=1); print $b"
but it doesn't?
I don't understand why you're assuming they *should* do the same thing.
Let's stop using shortcuts and spell each of these out:
sub f {
foreach (shift @_){
$_ = 5;
}
}
In this one, $_ is an alias to each element of the list that foreach
iterates over. @_ contains a list of aliases to f()'s arguments.
shift() remove and returns the first element of @_. So the list that
foreach iterates over is the first element of @_. Therefore, $_ is an
alias to an alias to the first argument of f().
sub f {
foreach (map { $_ } shift @_) {
$_ = 5;
}
}
In this one, foreach is not iterating over the first element of @_.
Instead, you're using map() to generate a new list, which will be
composed of the values passed to it. Within the map block itself, $_
is an alias to the first element of @_. The list that map returns
however, is not an alias. It is this list that foreach is iterating
over.
Paul Lalli