foreach localize variable to the loop.
use strict;
use warnings;
my $adr;
my $i = 0;
foreach $i(5..10){
$adr = \$i;
print "$i ($adr)\n";
}
$adr = \$i;
print "Outside loop i = $i ($adr)\n";
output
5 (SCALAR(0x9d1e1d8))
6 (SCALAR(0x9d1e1d8))
7 (SCALAR(0x9d1e1d8))
8 (SCALAR(0x9d1e1d8))
9 (SCALAR(0x9d1e1d8))
10 (SCALAR(0x9d1e1d8))
Outside loop i = 0 (SCALAR(0x9d343a0))
From perldoc,
The foreach loop iterates over a normal list value and sets the variable VAR to be each element of the list in turn. If the variable is preceded with the keyword my, then it is lexically scoped, and is therefore visible only within the loop. Otherwise, the variable is implicitly local to the loop and regains its former value upon exiting the loop. If the variable was previously declared with my, it uses that variable instead of the global one, but it's still localized to the loop. This implicit localization occurs only in a foreach loop.
To preserve value of $i you can use C like for loop,
my $i = 0;
for ($i = 5; $i <= 10; $i++) { .. }
although it's less readable than perl foreach
use strict; use warnings;at the top of every Perl script you write. Those two pragmas can save you a lot of painful debugging.