参数传递给Perl子例程的顺序是否显着?

cra*_*eld 1 perl

参数传递给Perl子例程的顺序是否显着?当我调试以下代码时:

my $loopCounter = 1;
foreach(@authors) {

   my @splitAffiliations = splitAffiliations($params);
   my @foundItems = findAffiliationForAuthor($_, @splitAffiliations, $loopCounter);

   # Process @foundItems

   $loopCounter++;
}

...

sub findAffiliationForAuthor {

   my ($author, @affiliations, $aIndex) = @_;

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

我发现变量$loopCounter在子程序findAffiliationForAuthor被调用之前有一个值,但在调用之后是未定义的.因此,子程序接收前两个参数的值而第三个参数没有任何值.但是,当我将参数的顺序更改为:

my @foundItems = findAffiliationForAuthor($loopCounter, $_, @splitAffiliations);
Run Code Online (Sandbox Code Playgroud)

$loopCounter保留的值并按预期传递子例程.

看起来我必须将我的所有标量变量放在我的数组变量之前,或者可能不会混合它们.听起来不错吗?

Kei*_*son 5

当然,订单很重要.

参数按照传递它们的顺序传递,并将数组参数展为参数列表.参数列表在子例程中显示为@_列表的内容.

你实际上不能将数组作为参数传递; 它的元素被提取并用任何其他参数推入列表中.

你遇到的问题是因为你处理参数的方式:

my ($author, @affiliations, $aIndex) = @_;
Run Code Online (Sandbox Code Playgroud)

$author@_像你想要的那样得到第一个元素,但是@affiliations把所有剩下的列表都弄清楚了.undef然后存储该值$aIndex.

您可以将单个数组传递给子例程,只要它是最后一个参数:

my($first_scalar, $second_scalar, @array) = @_;
Run Code Online (Sandbox Code Playgroud)

如果将多个数组传递给子例程:

foo(@array1, @array2);
Run Code Online (Sandbox Code Playgroud)

两个数组的元素被展平为一个列表,子程序无法知道哪个元素来自哪个数组参数.

您可以将引用传递给数组:

sub foo {
    my ($scalar1, $array_ref1, $scalar2, $array_ref2) = @_;
    # ...
}
Run Code Online (Sandbox Code Playgroud)

然后像这样调用它:

foo(42, \@array1, $some_scalar, \@array2);
Run Code Online (Sandbox Code Playgroud)