将'shift'分配给变量意味着什么?

sea*_*ran 21 variables perl

例:

use strict;
my $file = shift;

open(IN, $file) || die "Unable to open $file\n";
open(OUT, ">$file.$$") or die $!;
Run Code Online (Sandbox Code Playgroud)

这是怎么回事my $file = shift

TLP*_*TLP 28

如果在主程序中使用,它将shift(删除并返回)@ARGV程序的参数列表中的第一个值.如果在子例程中使用,它将从@_子参数列表中移出第一个值.有关详细信息,请参阅文档.


Die*_*lla 14

您可以阅读文档shift.很清楚.shift接受一个数组并提取第一个元素(实际上从数组中删除它).如果您不提供任何数组,它将使用@ARGV(程序命令行的参数)来读取数据.如果你在函数内部,它会使用函数@_的参数.

例:

my @array = (1, 2, 3);
my $value = shift @array;
print $value; # will print '1'
Run Code Online (Sandbox Code Playgroud)

  • 应该注意,该值也从原始数组中删除. (5认同)

Sma*_*nor 5

shift使用@_包含传递给函数的值的变量,或者如果在函数外部引用,则shift使用@ARGV传递给脚本本身的值shift.

一个注意事项:这可能是明智的,特别是在许多路径包含空格的Windows中,当您将文件名和路径传递给脚本或函数时,将文件名和路径放在单引号中.这将告诉Perl您传递的是单个标量值而不是值数组.如果要插入部分名称,可以使用双引号.例如:

my $path = 'C:\Goat Kids';
func("$path\\goat.txt");
Run Code Online (Sandbox Code Playgroud)

或者,如果要将文件名直接传递给脚本,请从命令行:

perl goat.pl "C:\Goat Kids\goat.txt"
Run Code Online (Sandbox Code Playgroud)


小智 5

前面的答案已经描述了如何shift工作。我想评论一下为什么在您自己的程序中使用它是一个好主意。

Perl 默认情况下是一种引用传递语言。如果子例程修改其参数,调用者将看到这些有时是意外的更改。shift将子例程参数分配给私有变量是一个很好的做法。这样,如果您对其进行任何更改,调用者将看不到它。例如,下面的代码输出

1
2
2
Run Code Online (Sandbox Code Playgroud)

第一个子例程修改其参数,调用者会看到更改。第二个子例程修改其参数的私有副本,并且此更改在调用者中不可见。

use strict;
use warnings;

sub pass_by_ref {
    $_[0] = 2;
}

sub pass_by_value {
    my $x = shift @_;
    $x = 3;
}

my $x = 1;
print $x, "\n";
pass_by_ref($x);
print $x, "\n";
pass_by_value($x);
print $x, "\n";
Run Code Online (Sandbox Code Playgroud)