鉴于此代码:
#!/usr/bin/perl -w
use strict;
use warnings;
sub foo {
return wantarray ? () : "value1";
}
my $hash = {
key1 => foo(),
key2 => 'value2'
};
use Data::Dumper;
print Dumper($hash);
我得到以下输出:
$VAR1 = {
'key1' => 'key2',
'value2' => undef
};
我期待的时候:
$VAR1 = {
'key1' => 'value1',
'key2' => 'value2'
};
据我所知,散列是一种偶数大小的数组(正如我所得到的“散列分配中的奇数元素数量”警告所示)但散列元素只能是标量,为什么编译器会给它数组上下文?
我在直接分配给哈希时使用CGI模块的param函数找到了这个。上面的foo()函数是对CGI :: param('mistyped_url_param')的调用,它返回一个空数组,破坏(旋转?)哈希结构。
答案 0 :(得分:7)
fat逗号不是特殊的哈希赋值运算符。它只是一段语法糖,意思是“自动引用前一个东西”
所以:
my $hash = {
key1 => foo(),
key2 => 'value2'
};
意思是:
my $hash = {
'key1', foo(), 'key2', 'value2'
};
......这是一份清单,正如威勒特所说:
列表中的每个表达式都在列表上下文中计算。您可以致电
来解决这个问题scalar foo()
答案 1 :(得分:3)
匿名哈希构造函数为其中的内容提供列表上下文,因为它需要键和值列表。就是这样,因为它就是这样。我们没有办法在代码中表示Perl哈希,因此您必须使用我们交替键和值的列表。 =>
符号在视觉上对我们有所帮助,但没有任何魔法可以帮助Perl找出各种各样的东西。
当前上下文传播给子程序调用等,就像在任何其他情况下一样。
这允许您使用列表操作构建哈希:
my $hash = {
a => 'A',
map( uc, 'd' .. 'f' ),
return_list( @args ),
z => 'Z'
};
如果您需要在标量上下文中使用某些内容,请使用scalar
:
my $hash = {
a => 'A',
map( uc, 'd' .. 'f' ),
'g' => scalar return_item( @args ),
z => 'Z'
};