Perl函数原型

Perl函数原型,perl,function-prototypes,Perl,Function Prototypes,为什么我们在Perl中使用函数原型? 有哪些不同的原型可用?如何使用它们 示例:$$,$@,\@它们是什么意思?您可以在官方文档中找到描述: 但更重要的是:阅读为什么不应该使用函数prototytpes“要编写一些函数,原型是绝对必要的,因为它们改变了参数传递的方式、子调用的解析以及参数在什么上下文中求值 下面讨论了内置的open和bless的原型,以及对用户编写的代码(如fold\u left子例程)的影响。我得出的结论是,有一些场景是有用的,但它们通常不是处理签名的好机制 示例:CORE::

为什么我们在Perl中使用函数原型? 有哪些不同的原型可用?如何使用它们


示例:
$$,$@,\@
它们是什么意思?

您可以在官方文档中找到描述:


但更重要的是:阅读为什么不应该使用函数prototytpes“

要编写一些函数,原型是绝对必要的,因为它们改变了参数传递的方式、子调用的解析以及参数在什么上下文中求值

下面讨论了内置的
open
bless
的原型,以及对用户编写的代码(如
fold\u left
子例程)的影响。我得出的结论是,有一些场景是有用的,但它们通常不是处理签名的好机制

示例:
CORE::open
一些内置函数有原型,例如
open
。您可以获得任何函数的原型,如
说原型“CORE::open”
。我们得到
*;$@
。这意味着:

  • *
    采用裸字、glob、globref或标量。例如
    STDOUT
    my$fh
  • 使以下参数成为可选参数
  • $
    在标量上下文中计算下一个项目。我们将在一分钟内看到为什么这是好的
  • @
    允许任意数量的参数
这允许像这样的调用

  • openfoo;
    非常糟糕的风格,相当于
    openfoo,我们的$FOO
  • 打开我的$fh,@array;
    ,解析为
    打开我的$fh,scalar(@array)
    。无用

  • open my$fh,“有关预定义变量,请参阅。他不是在谈论变量,而是在谈论原型。一般来说,我们不是。
    
    sub fold_left {
      my $code = shift;
      while ($#_) { # loop while more than one element
        my ($x, $y) = splice @_, 0, 2;
        unshift @_, $code->($x, $y);
      }
      return $_[0];
    }
    
    my $sum = fold_left sub{ $_[0] + $_[1] }, 1 .. 10;
    my $str = fold_left sub{ "$_[0] $_[1]" }, 1 .. 10;
    my $undef = fold_left;
    my $runtime_error = fold_left \"foo", 1..10;
    
    sub fold_left (&@) { ... }
    
    my $sum = fold_left { $_[0] + $_[1] } 1 .. 10; # aka List::Util::sum(1..10);
    my $str = fold_left { "$_[0] $_[1]" } 1 .. 10; # aka join " ", 1..10;
    my $compile_error1 = fold_left;                # ERROR: not enough arguments
    my $compile_error2 = fold_left "foo", 1..10;   # ERROR: type of arg 1 must be sub{} or block.
    
    sub mypush (\@@) {
      my ($arrayref, @push_these) = @_;
      my $len = @$arrayref;
      @$arrayref[$len .. $len + $#push_these] = @push_these;
    }
    
    my @array;
    mypush @array, 1, 2, 3; 
    
    my $array = [];
    mypush @$array, 1, 2, 3;
    
    sub mypush (+@) { ... }
    
    my @array;
    mypush @array, 1, 2, 3;
    my $array_ref = [];
    mypush $array_ref, 1, 2, 3; # works as well! yay
    my %hash;
    mypush %hash, 1, 2, 3; # syntactically legal, but will throw fatal on dereferencing.
    mypush "foo", 1, 2, 3; # ditto
    
    sub each_array (\@;\@\@\@\@\@\@\@\@\@\@\@\@\@\@\@\@\@\@\@\@\@\@\@\@) {
        return each_arrayref(@_);
    }