\&和$ expr的用法是什么 - >()

All*_*len 3 perl

sub reduce(&@) {

    my $expr = \&{shift @ARG};

    my $result = shift @ARG;
    while (scalar @ARG > 0) {
        our $a = $result;
        our $b = shift @ARG;
        $result = $expr->();
    }

    return $result;
}
Run Code Online (Sandbox Code Playgroud)

我无法真正理解这段代码中的一些语法.有人可以向我解释一下吗?喜欢\&$result = $expr->()

ike*_*ami 8

\&name返回对名为的子例程的引用name.

$code_ref->()调用引用的子例程$code_ref.

$ perl -e'
    sub f { CORE::say "Hi" }
    my $code_ref = \&f;
    $code_ref->();
'
Hi
Run Code Online (Sandbox Code Playgroud)

在您的情况下,shift @ARG返回子例程引用,所以

my $expr = \&{shift @ARG};
Run Code Online (Sandbox Code Playgroud)

本来可以写成

my $expr = shift @ARG;
Run Code Online (Sandbox Code Playgroud)

这有点像做$y = $x+1-1;.


请注意,reduce原型允许将其称为

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

但实际执行的是

reduce(sub { ... }, ...)
Run Code Online (Sandbox Code Playgroud)

请注意,这个版本reduce是错误的.您应该使用List :: Util提供的那个.

  • local $alocal $b本来应该用来避免重挫它的调用者可能在价值观$a$b.
  • 这个版本reduce期望它的回调被编译在与reduce自身相同的包中.否则,回调子将无法简单地使用$a$b.
  • our在这个版本的情况下,声明变量使用实际上是完全无用的,因为$a并且$b免于use strict;检查,并且未声明的使用$a$b将访问相同的包变量.