在perl中使用\和{},[]引用变量有什么区别?

chi*_*ori 3 perl

下面的代码工作正常,但如果我替换push @array,{%hash},push @array,\%hash那么它没有.有人可以帮我理解差异.我相信{%hash}是指匿名哈希.这是否意味着匿名哈希的寿命比对命名哈希(\%hash)的引用要长.

use strict;
use warnings;
use Data::Dumper;
my @array;
my %hash;
%hash = ('a' => 1,
         'b' => 2,
         'c' => 3,);

push @array,{%hash};

%hash = ('e' => 1,
         'f' => 2,
         'd' => 3,);

push @array,{%hash};

print Dumper \@array;
Run Code Online (Sandbox Code Playgroud)

产量

$VAR1 = [
          {
            'c' => 3,
            'a' => 1,
            'b' => 2
          },
          {
            'e' => 1,
            'd' => 3,
            'f' => 2
          }
        ];
Run Code Online (Sandbox Code Playgroud)

更新 以下是我正在处理的实际代码.我认为在这种情况下,参考的副本是我认为唯一可行的解​​决方案.如果我错了,请纠正我.

use Data::Dumper;
use strict;
use warnings;

my %csv_data;
my %temp_hash;
my @cols_of_interest = qw(dev_file test_file diff_file status);
<DATA>; #Skipping the header
while (my $row = <DATA>) {
    chomp $row;
    my @array = split /,/,$row;
    @temp_hash{@cols_of_interest} = @array[3..$#array]; 
    push @{$csv_data{$array[0]}{$array[1] . ':' . $array[2]}},{%temp_hash};
}
print Dumper \%csv_data;

__DATA__
dom,type,id,dev_file,test_file,diff_file,status
A,alpha,1234,dev_file_1234_1.txt,test_file_1234_1.txt,diff_file_1234_1.txt,pass
A,alpha,1234,dev_file_1234_2.txt,test_file_1234_2.txt,diff_file_1234_2.txt,fail
A,alpha,1234,dev_file_1234_3.txt,test_file_1234_3.txt,diff_file_1234_3.txt,pass
B,beta,4567,dev_file_4567_1.txt,test_file_4567_1.txt,diff_file_4567_1.txt,pass
B,beta,4567,dev_file_4567_2.txt,test_file_4567_2.txt,diff_file_4567_2.txt,fail
C,gamma,3435,dev_file_3435_1.txt,test_file_3435_1.txt,diff_file_3435_1.txt,pass
D,hexa,6768,dev_file_6768_1.txt,test_file_6768_1.txt,diff_file_6768_1.txt,fail
Run Code Online (Sandbox Code Playgroud)

sim*_*que 13

双方\%hash{%hash}创建引用,但它们引用两个不同的东西.

\%hash是一个参考%hash.如果取消引用,其值将随着值的变化而变化%hash.

{%hash}从中的值创建新的匿名哈希引用%hash.它创建了一个副本.这是在Perl 中创建数据结构的浅表副本的最简单方法.如果您更改%hash,此副本不会受到影响.


变量存在多长时间与变量的类型或创建方式无关.只有范围与此相关.Perl中的引用在这里是一个特殊情况,因为有一个内部引用计数器可以跟踪对值的引用,因此如果某个地方仍有引用,即使它超出范围,它也会保持活动状态.这就是为什么这样做的原因:

sub frobnicate {
    my %hash = ( foo => 'bar' );
    return \%hash;
}
Run Code Online (Sandbox Code Playgroud)

如果你想撇清从初始值的参考,你需要把它变成一个弱引用通过weaken标量::的Util.这样,引用计数不会受其影响,但它仍将与值相关,而副本则不会.

有关参考的更多信息,请参阅perlrefperlreftut.这个问题涉及如何查看引用计数.关于它的描述也可以在perlguts中的Reference Counts and Mortality一章中找到.