【问题标题】:Does Anyone Know How to Understand Such Kind of Perl Code Blocks?有谁知道如何理解这种 Perl 代码块?
【发布时间】:2014-07-02 19:12:54
【问题描述】:

我对 Perl 命名块感到困惑(我以为它们是......)。下面是一个例子:

#!/usr/bin/perl

sub Run(&){
  my ($decl) = @_;
  $decl->();  
}

sub cmd(&){
  my($decl)   = @_;
  my(@params) = $decl->();
  print "@params\n";
}
sub expect(&){
  my ($decl) = @_;  
  my(@params) = $decl->();
  print "@params\n";
}

Run {
  cmd { "echo hello world " };
  expect { exit_code => 0, capture => 2}; 
};

注意最后几行。看起来“Run”、“cmd”、“expect”是命名块,而不是函数。有谁知道它们是什么?任何可用的链接介绍它们? 我找不到这种语法的任何参考。

【问题讨论】:

    标签: perl


    【解决方案1】:

    让我们解读Run的这个定义:

    sub Run(&){
      my ($decl) = @_;
      $decl->();  
    }
    

    它表示称为Run 的子程序,它接受CODE 类型的参数(这就是它使用(&) 的原因)。在其中$decl 被分配给传递的代码,而这个代码被$decl->(); 调用。

    现在,您的示例中的最后几行:

    Run {
      cmd { "echo hello world " };
      expect { exit_code => 0, capture => 2}; 
    };
    

    等价于:

    Run(sub {
      cmd { "echo hello world " };
      expect { exit_code => 0, capture => 2}; 
    });
    

    换句话说,它使用大括号中的匿名过程代码调用Run

    【讨论】:

    • 感谢您的友好回答。这就是我想要的。
    【解决方案2】:

    Runcmdexpectprototype 定义的函数,它们像内置函数一样工作(无需编写 sub{..},因为这是隐含的 (&) 签名函数)。

    如果这些函数是在没有原型的情况下定义的,

    sub Run { .. }
    sub cmd { .. }
    sub expect { .. }
    

    那么显式 sub{} 参数将不是可选的而是必需的,

    Run(sub{
      cmd(sub{ "echo hello world " });
      expect(sub{ exit_code => 0, capture => 2}); 
    });
    

    【讨论】:

      【解决方案3】:

      它们是接受块作为参数的子程序。请参阅:http://perldoc.perl.org/perlsub.html#Prototypes。他们定义中的(&) 意味着他们的第一个参数是一段代码。

      【讨论】:

        猜你喜欢
        • 2021-09-18
        • 2016-05-13
        • 2012-09-08
        • 1970-01-01
        • 2022-11-03
        • 2014-03-31
        • 1970-01-01
        • 2016-03-06
        相关资源
        最近更新 更多