I think that one of the things that's mildly confusing in this area is that perl does an implicit "local" for you
whenever it sets $_ for you (in foreach, map and grep loops), but if you do the setting of $_ yourself, then you've got a new problem you don't see otherwise.
(I still don't understand why our "standard practice" doesn't include doing a "local $_" at the beginning of every sub... but then on the other hand, I guess it isn't all that common to get burned by $_ problems.)
Anyway, here's a script that demos what I'm talking about:
use warnings;
use strict;
use Test::More qw(no_plan);
# we're going to try doing various things to $_,
# and we want to see if it changes the initial value
my $initial_value = 'Some Value';
my @initial_array = qw( wun tew thuree foah fahv sex sevhun );
{#1 map perlfunc: "locally setting $_ to each element"?
my $testcase = "map";
my @array = @initial_array;
$_ = $initial_value;
my @whateva = map{ s/^f/F/ } @array;
is( $_, $initial_value, $testcase);
}
{#2 foreach
my $testcase = "foreach";
my @array = @initial_array;
$_ = $initial_value;
my @whateva = ();
foreach (@array) { s/^f/F/; push @whateva, $_ };
is( $_, $initial_value, $testcase);
}
{#3 while - this one fails
my $testcase = "while";
my @array = @initial_array;
$_ = $initial_value;
my @whateva = ();
while (@array) { $_ = pop @array; s/^f/F/; push @whateva, $_};
is( $_, $initial_value, $testcase);
}
{#4 while with local
my $testcase = "while with explicit local";
my @array = @initial_array;
$_ = $initial_value;
my @whateva = ();
while (@array) { local $_ = pop @array; s/^f/F/; push @whateva, $_};
is( $_, $initial_value, $testcase);
}
{#5 grep
my $testcase = "grep";
my @array = @initial_array;
$_ = $initial_value;
my @whateva = grep{ m/^f/ } @array;
is( $_, $initial_value, $testcase);
}
-
Are you posting in the right place? Check out Where do I post X? to know for sure.
-
Posts may use any of the Perl Monks Approved HTML tags. Currently these include the following:
<code> <a> <b> <big>
<blockquote> <br /> <dd>
<dl> <dt> <em> <font>
<h1> <h2> <h3> <h4>
<h5> <h6> <hr /> <i>
<li> <nbsp> <ol> <p>
<small> <strike> <strong>
<sub> <sup> <table>
<td> <th> <tr> <tt>
<u> <ul>
-
Snippets of code should be wrapped in
<code> tags not
<pre> tags. In fact, <pre>
tags should generally be avoided. If they must
be used, extreme care should be
taken to ensure that their contents do not
have long lines (<70 chars), in order to prevent
horizontal scrolling (and possible janitor
intervention).
-
Want more info? How to link
or How to display code and escape characters
are good places to start.