在$ _ [0]的情况下解除引用,$ _ [1] .....等等

Abh*_*rma 7 perl

请看下面的代码:

$scalar = 10;

subroutine(\$scalar);

sub subroutine {
    my $subroutine_scalar = ${$_[0]}; #note you need the {} brackets, or this doesn't work!
    print "$subroutine_scalar\n";
}
Run Code Online (Sandbox Code Playgroud)

在上面的代码中,您可以看到写下的注释"请注意您需要{}括号,否则这不起作用!" .请解释为什么我们不能使用相同的声明的原因:

my $subroutine_scalar = $$_[0];
Run Code Online (Sandbox Code Playgroud)

即不使用花括号.

TLP*_*TLP 9

很多人已经在这里给出了正确答案.我想添加一个我发现有启发性的例子.您可以阅读perldoc perlref中的文档以获取更多信息.

您的问题是模糊不清,您有两个操作$$[0]处理相同的标识符_,结果取决于首先执行的操作.我们可以通过使用支撑花括号使其不那么模糊${ ... }.$$_[0]可能(对于人类而言)可能意味着:

  • ${$$_}[0]- 取消引用标量$_,然后取其第一个元素.
  • ${$_[0]}- 获取0数组的元素@_并取消引用它.

正如你所看到的,这两种情况涉及到完全不同的变量,@_$_.

当然,对于Perl来说它并不含糊,我们只是得到第一个选项,因为在键查找之前执行解除引用.我们需要支持花括号来覆盖这种解除引用,这就是为什么你的例子没有支持括号就"工作"的原因.

您可能会考虑为子例程稍微混淆一些功能.您可以分两个阶段完成,而不是尝试一次做两件事(获取参数并取消引用它):

sub foo {
    my $n = shift;
    print $$n;
}
Run Code Online (Sandbox Code Playgroud)

在这里,我们采取的第一个参数关@_shift,然后取消对它的引用.干净简单.

但是,大多数情况下,您不会使用对标量变量的引用.在这些情况下,您可以使用箭头运算符->

my @array = (1,2,3);
foo(\@array);

sub foo {
    my $aref = shift;
    print $aref->[0];
}
Run Code Online (Sandbox Code Playgroud)

我发现使用箭头运算符比$$语法更好.