我想调用 perl脚本(B.pl),它将从主 perl脚本(A.pl)列出远程服务器中可用的文件传递多个可选参数。
由于参数是可选的,如果我使用反引号,则参数将被分配给B.pl中的错误变量。
如果我使用/etc
,那么虽然有些参数是未定义的,但它在B.pl中被正确分配但是STDOUT没有被分配给调用脚本中的@list。
我是perl的新手,请在这个场景中指导。有没有办法用反引号传递空参数?
在A.pl:
@list=system(B.pl, argv0, argv1, argv2);
在B.pl:
my @filelist = system( B.pl, $argv0, $argv1, $argv2, $argv3);
my @filelist1 = `B.pl $argv0 $argv1 $argv2 $argv3`;
答案 0 :(得分:4)
您可以使用"零长度字符串" (""
或''
)作为反向标记内的参数:
perl -e "print `perl -e 'print $ARGV[2]' 0 '' 2`"
OR 使用perl模块处理命令行选项,例如的Getopt ::标准
答案 1 :(得分:2)
这不是关于Perl的问题,而是关于shell的问题。您正在尝试传递一组参数,其中一些是可选的。幸运的是,这是一个众所周知的问题。答案是传递命名选项而不是位置参数。在Perl中执行此操作的标准方法是使用Getopt::Long
。
例如,在B.pl
中,您可以说
use Getopt::Long;
my ($loc, $msk, $usr, $usr1);
GetOptions(
"loc=s" => \$loc,
"msk=s" => \$msk,
"usr=s" => \$usr,
"usr1=s" => \$usr1,
) or die "Something wrong with your options!";
A.pl
中的调用将为:
my @filelist1 = `B.pl '--loc=$argv0' '--msk=$argv1' '--usr=$argv2' '--usr1=$argv3'`;
有更复杂的方法。例如,根据this answer,我们会发现IPC::Run
。
答案 2 :(得分:1)
不幸的是,反引号运算符或readpipe
的安全版本不存在。它已经在perl
TODO列表上多年了!
但您可以使用open
轻松自己完成:
open my $handle, '-|', 'B.pl', $argv0, $argv1, $argv2, $argv3
or die "unable to run external command: $!";
my $output = do { local $/; <$handle> };
close $handle
or die "unable to capture output from child command: $!";
$? and die "remote command exited with non zero return code: $?";