如何使用散列作为Perl中子例程的参数?

7 perl hash reference

我有一个函数正在进行一些计算,然后将一些属性传递到另一个子例程,如下所示:

sub get_result {
    my $id = 1;     
    my %diet = ( result  => 28, 
                 verdict => 'EAT MORE FRUIT DUDE...'     
               );

    my %iq = ( result   => 193, 
               verdict => 'Professor Einstien'   
             );           
    print_result($id, %diet, %iq);
}

sub print_result {     
    my $id = shift;     
    my %d  = @_;     
    my %i  = @_;     

    print "IQ: $id\n";     
    print "DIET RESULT: $d{result}\n";     
    print "DIET VERDICT: $d{verdict}\n";     
    print "IQ RESULT: $i{result}\n";     
    print "IQ VERDICT: $i{verdict}\n";     
}     
Run Code Online (Sandbox Code Playgroud)

我的问题是在(DIET RESULT,DIET VERDICT)和(IQ SCORE,IQ RESULT)中打印的结果都是相同的.好像变量%d和%i正在填充相同的变量.任何想法为什么会这样?

如果我尝试移动所有三个变量,如下所示:

my $id = shift;     
my %d  = shift;     
my %i  = shift; 
Run Code Online (Sandbox Code Playgroud)

我收到以下错误:

Odd number of elements in hash assignment
Run Code Online (Sandbox Code Playgroud)

inn*_*naM 25

将数组(或散列)传递给子例程时,子例程将获取值(或键值对)的列表.这就是为什么你不能传递两个数组(或两个哈希)的原因,因为子程序不会知道第一个数组的结束位置和第二个数组的开始位置.

若要解决此问题,您应该传入引用:

my %hash1 = ( foo => 'bar' );
my %hash2 = ( bar => 'baz' );
subroutine( \%hash1, \%hash2 );

sub subroutine {
    my ( $hashref1, $hashref2 ) = @_;
    print $hasref1->{foo}, $hashref2->{bar};
}
Run Code Online (Sandbox Code Playgroud)

PS:除了概念问题,你的代码还具有以下功能:

my %d  = @_;     
my %i  = @_;     
Run Code Online (Sandbox Code Playgroud)

如果%d和%i都被赋予相同的值,那么在它们之后相同时不应该出乎意料.

  • 如果您接受了答案,那么对其他人可能会有所帮助.(不是我会以任何方式介意25个声望点.) (3认同)

bri*_*foy 5

您可能想看看我的书Intermediate Perl,其中大约三分之一涉及参考以及如何使用它们.这包括将复杂的数据结构传递到子例程以及引用使您的生活更轻松的其他方式.:)

some_sub( \%hash );
some_sub( { key => 'value' } );
some_sub( $hash_ref );

sub some_sub {
    my( $hash_ref ) = @_;

    ...
    }
Run Code Online (Sandbox Code Playgroud)