我喜欢哈希切片并经常使用它们:
my %h;
@h{@keys}=@vals;
工作出色!但有两件事总是让我烦恼。
首先,是否可以将上面的两行组合成一行代码?声明哈希并立即填充它会很好。
其次,是否可以对现有的匿名哈希进行切片......如:
my $slice=$anonh->{@fields}
答案 0 :(得分:8)
关于第一个问题,请在一行代码中执行:
@$_{@keys}=@vals for \my %h;
或
map @$_{@keys}=@vals, \my %h;
但我不会这样做;这是一种令人困惑的写作方式。
任一版本声明变量并立即对其进行引用并将$_
别名为引用,以便可以在切片中使用哈希引用。这允许您在现有范围中声明变量; @{ \my %h }{@keys} = @vals;
也“有效”,但有一个不幸的缺点,就是将%h
范围限定在哈希切片中的那个小块上。
对于第二个问题,如上所示,切片可用于哈希引用;有关易于记忆的规则,请参阅http://perlmonks.org/?node=References+quick+reference。
my @slice = @$anonh{@fields};
或者你的意思是:
my $slice = [ @$anonh{@fields} ];
但@ slice / $ slice有一个值的副本。要获取哈希值的别名数组,您可以执行以下操作:
my $slice = sub { \@_ }->( @$anonh{@fields} );
答案 1 :(得分:8)
第一个问题:
my %h = map { $keys[$_] => $vals[$_] } 0..$#keys;
或
use List::MoreUtils qw( mesh );
my %h = mesh @keys, @vals;
第二个问题:
如果哈希为...NAME...
,则哈希引用为...{ $href }...
,所以
my @slice = @hash{@fields};
是
my @slice = @{ $anonh }{@fields};
如果引用表达式是变量,则curlies是可选的。
my @slice = @$anonh{@fields};
答案 2 :(得分:3)
哈希切片语法是
@ <hash-name-or-hash-ref> { LIST }
当您对哈希引用进行切片时,请将其括在花括号中,以便它不会被解除引用为数组。这给你:
my @values = @{$anonh}{@fields}
表示哈希引用$anonh
。