【问题标题】:How to pass variables to a function as reference and get them changed in caller without returning如何将变量作为引用传递给函数并在调用者中更改它们而不返回
【发布时间】:2019-09-24 20:16:48
【问题描述】:

我需要将变量、列表和哈希传递给子例程,并从中取回更改而不返回。

这段代码不能完成这项工作。

sub foo{
    my $one = {$_[0]};   
    my @list = @{$_[1]};
    my %hash = %{$_[2]};
    print("\n inside foo: ${one}\n");
    print("\n inside foo: $one @list $hash{'key'}\n");
    $one = 2;
    @list = (4,5,6);
    my %hash2;
    $hash2{'key'} = 'valueModified';    
    %hash = %hash2;
    print("\n inside foo after Mod: $one\n");
    print("\n inside foo after Mod: $one @list $hash{'key'}\n");
}

my $one = 1;
my @list = (1,2,3);
my %hash;
$hash{'key'} = 'value';
my @allLocalArgs = (\$one,\@list,\%hash);
foo(\@allLocalArgs);
print("\nafter foo modification: $one @list $hash{'key'}\n");

输出:

 inside foo: HASH(0x234a240)

 inside foo: HASH(0x234a240)  

 inside foo after Mod: 2

 inside foo after Mod: 2 4 5 6 valueModified

after foo modification: 1 1 2 3 value

谢谢。

【问题讨论】:

  • 这叫数组,不是列表。

标签: arrays list perl reference subroutine


【解决方案1】:

原则上,几乎在任何语言中,您都希望传递引用调用者中的数据结构的对象、指针或引用。在 Perl 中,这将是一个参考——而您正在这样做。

但是然后在 sub 中创建本地副本; $one@list%hash 在子中是 lexical variables 本地到sub's scope,屏蔽/隐藏调用范围内的那些。对这些的更改不会超出 sub 的范围。

相反,直接使用您传递的引用来写入调用者的数据。

sub foo { 

    my ($rscalar, $rary, $rhash) = @_;

    $$rscalar = 2;

    @$rary = (4,5,6);

    $rhash->{'key'} = 'valueModified'; 
}

foo(\$one, \@list, \%hash);

现在调用代码中的$one@list%hash已更改。有关使用参考的详细信息,请参阅教程perlreftut 和参考perlref

请注意,foo(\@allLocalArgs); 使用参数传递数组的引用,因此 sub 接收一个元素——该数组的引用。你可以这样做,但就问题而言,它不是必需的,所以我删除了它并直接传递了参数列表。

要注意的另一件事是参数在@_ 中具有别名——因此,如果在子程序中您直接使用@_,那么您可以更改调用者中的数据。因此,如果您要将标量变量作为foo($one) 传递,那么子中的$_[0] = 2 会更改调用者中的$one我认为原则上最好避免;如果要更改调用者的数据,则应尽可能明确;通过引用。


术语说明

Perl 中的 list 是一种难以捉摸的短暂结构,用于在程序中移动数据;想想堆栈上某处的一堆标量(值),即将被使用并消失。可能是将参数传递给函数(foo($v1, $v2)),或者形成一个字符串(join '', $v1, $v2),或者创建一个匿名数组引用([$v1, $v2])等等。

另一方面,数组是一个多值变量。很像哈希(关联数组)是一个多值变量,与 scalar 不同的是,它是一个单值变量。

这方面已经写了很多;这里有一些很容易出现的链接:Effective Perler article(包含更多文章的链接)和 Stackoverflow 页面Perl array vs list

简而言之,您问的是“标量、数组、哈希”。

【讨论】:

猜你喜欢
  • 1970-01-01
  • 2013-06-07
  • 1970-01-01
  • 2015-08-02
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-12-29
  • 1970-01-01
相关资源
最近更新 更多