I noticed that the Parallel::Loops module uses $_ as the argument to its subref. This question isn't about Parallel::Loops per-se, it is about the coderef calling convention.
This is their example, note that $_ is passed to the sub:
$pl->foreach( \@parameters, sub {
# This sub "magically" executed in parallel forked child
# processes
# Lets just create a simple example, but this could be a
# massive calculation that will be parallelized, so that
# $maxProcs different processes are calculating sqrt
# simultaneously for different values of $_ on different CPUs
# (Do see 'Performance' / 'Properties of the loop body' below)
$returnValues{$_} = sqrt($_);
});
...but I've always used $_[0] or @_ for values passed to a sub:
$a = sub { print "\$_=$_\n" ; print "\$_[0]=$_[0]\n" };
$a->(1);
# prints out
# $_=
# $_[0]=1
Notice in my example $_ didn't work, but $_[0] (ie, @_) does. What is different between the coderef in Parallel::Loops's example, and the coderef in my example?
Note that their example isn't a typo: it only works if you use $_, which is why I'm posing this question.
Look in the module source when you want to know how it's doing its thing :)
In
Parallel::Loops::foreach, the module sets$_before it calls the subroutine you provided. Since this is in a forked process, it doesn't do anything to protect the value of$_. Notice the various layers of code refs in that module.You could do that same thing. Every time you want to run your code ref, set the value of
$_first:Take a look at Mojo::Collection, for example, that does this with its code refs. List::Util has several utilities that do this too.