@list[2]
有效,因为它是列表的一部分。
在 Perl 5 中,sigil 表示——在非技术意义上——你的表达式的上下文。除了切片在标量上下文中的一些非标准行为外,基本思想是 sigil 表示您想从表达式中得到什么。
如果你想要一个散列的标量,它是$hash{key}
. 如果你想要一个数组中的标量,它是$array[0]
. 但是,Perl 允许您获取聚合的切片。这允许您在一个紧凑的表达式中检索多个值。切片采用索引列表。所以,
@list = @hash{ qw<key1 key2> };
为您提供哈希中的项目列表。和,
@list2 = @list[0..3];
为您提供数组中的前四个项目。--> 对于您的情况,@list[2]
仍然有一个索引“列表”,只是该列表是“一个列表”的特例。
由于标量和列表上下文定义得相当好,并且没有“散列上下文”,它在$
标量和@
“列表”中保持相当稳定,直到最近,Perl 不支持使用%
. 所以既没有%hash{@keys}
也%hash{key}
没有意义。但是,现在,您可以通过将%
印记放在前面来转储具有值的索引对。
my %hash = qw<a 1 b 2>;
my @list = %hash{ qw<a b> }; # yields ( 'a', 1, 'b', 2 )
my @l2 = %list[0..2]; # yields ( 0, 'a', 1, '1', 2, 'b' )
所以,我想,如果你有旧版本的 Perl,你不能,但如果你有 5.20,你可以。
但是为了一个完整主义者的缘故,切片有一种非直观的方式,它们在标量环境中工作。因为将列表放入标量上下文的标准行为是对列表进行计数,如果切片与该行为一起使用:
( $item = @hash{ @keys } ) == scalar @keys;
这将使表达式:
$item = @hash{ @keys };
不比以下更有价值:
scalar @keys;
因此,Perl 似乎将其视为表达式:
$s = ( $hash{$keys[0]}, $hash{$keys[1]}, ... , $hash{$keys[$#keys]} );
当在标量上下文中计算逗号分隔的列表时,它会分配最后一个表达式。所以它真的结束了
$item = @hash{ @keys };
不比以下更有价值:
$item = $hash{ $keys[-1] };
但它使编写如下:
$item = $hash{ source1(), source2(), @array3, $banana, ( map { "$_" } source4()};
比写作稍微容易一些:
$item = $hash{ [source1(), source2(), @array3, $banana, ( map { "$_" } source4()]->[-1] }
但只是轻微的。