Perl:这段代码怎么可能工作?
Perl: How is it possible that this code is working?
my %hash = ('red' => "John", 'blue' => "Smith");
func (%hash);
sub func {
my $hash = $_[0];
print "$hash{'red'}\n";
print "$hash{'blue'}\n";
}
我向子例程发送了一个散列,这个散列被视为标量。如果是这样,我怎么可能通过调用它的键来转向散列中的值?
因为你的%hash
范围是整个程序。
func(%hash);
相当于
func('red', 'John', 'blue', 'Smith');
-or-
func('blue', 'Smith', 'red', 'John');
所以
my $hash = $_[0];
相当于
my $hash = 'red';
-or-
my $hash = 'blue';
完全没用。幸好你再也不用 $hash
了。
相反,您使用在 sub 外部声明的 %hash
。您可以通过重新排序代码或限制 %hash
.
的范围(可见性)来查看这一点
use strict;
use warnings;
{
my %hash = ('red' => "John", 'blue' => "Smith");
func(%hash);
}
sub func {
my $hash = $_[0];
print "$hash{'red'}\n";
print "$hash{'blue'}\n";
}
$ perl a.pl
Global symbol "%hash" requires explicit package name at a.pl line 11.
Global symbol "%hash" requires explicit package name at a.pl line 12.
Execution of a.pl aborted due to compilation errors.
解决方法是传递引用。
use strict;
use warnings;
{
my %hash = ('red' => "John", 'blue' => "Smith");
func(\%hash);
}
sub func {
my $hash = $_[0];
print "$hash->{'red'}\n";
print "$hash->{'blue'}\n";
}
%hash is supposed to be local. no?
它在封闭范围内是局部的。范围由大括号分隔。但是你的声明周围没有大括号:
my %hash;
因此,%hash
在文件的每个嵌套范围内都可见。这是一个例子:
use strict;
use warnings;
use 5.016;
my $str = "hello";
if (1) { #new scope starts here
say "if: $str";
} #scope ends here
{ #new scope starts here
my $planet = "world";
say "block: $str";
for (1..2) { #new scope starts here
say "for: $str $planet";
} #scope ends here
} #scope ends here
#say $planet; #The $planet that was previously declared isn't visible here, so this looks
#like you are trying to print a global variable, which results in a
#compile error, because global variables are illegal with: use strict;
--output:--
if: hello
block: hello
for: hello world
for: hello world
my %hash = ('red' => "John", 'blue' => "Smith");
func (%hash);
sub func {
my $hash = $_[0];
print "$hash{'red'}\n";
print "$hash{'blue'}\n";
}
我向子例程发送了一个散列,这个散列被视为标量。如果是这样,我怎么可能通过调用它的键来转向散列中的值?
因为你的%hash
范围是整个程序。
func(%hash);
相当于
func('red', 'John', 'blue', 'Smith');
-or-
func('blue', 'Smith', 'red', 'John');
所以
my $hash = $_[0];
相当于
my $hash = 'red';
-or-
my $hash = 'blue';
完全没用。幸好你再也不用 $hash
了。
相反,您使用在 sub 外部声明的 %hash
。您可以通过重新排序代码或限制 %hash
.
use strict;
use warnings;
{
my %hash = ('red' => "John", 'blue' => "Smith");
func(%hash);
}
sub func {
my $hash = $_[0];
print "$hash{'red'}\n";
print "$hash{'blue'}\n";
}
$ perl a.pl
Global symbol "%hash" requires explicit package name at a.pl line 11.
Global symbol "%hash" requires explicit package name at a.pl line 12.
Execution of a.pl aborted due to compilation errors.
解决方法是传递引用。
use strict;
use warnings;
{
my %hash = ('red' => "John", 'blue' => "Smith");
func(\%hash);
}
sub func {
my $hash = $_[0];
print "$hash->{'red'}\n";
print "$hash->{'blue'}\n";
}
%hash is supposed to be local. no?
它在封闭范围内是局部的。范围由大括号分隔。但是你的声明周围没有大括号:
my %hash;
因此,%hash
在文件的每个嵌套范围内都可见。这是一个例子:
use strict;
use warnings;
use 5.016;
my $str = "hello";
if (1) { #new scope starts here
say "if: $str";
} #scope ends here
{ #new scope starts here
my $planet = "world";
say "block: $str";
for (1..2) { #new scope starts here
say "for: $str $planet";
} #scope ends here
} #scope ends here
#say $planet; #The $planet that was previously declared isn't visible here, so this looks
#like you are trying to print a global variable, which results in a
#compile error, because global variables are illegal with: use strict;
--output:--
if: hello
block: hello
for: hello world
for: hello world