0

我有一段python代码,我需要将它转换为perl,但不幸的是我不擅长perl,如果问题很简单,很抱歉。我想检查 STDOUT 和 STDERR 的特定单词。这是python代码:

p = subprocess.Popen("bmod -b " + beginTime + " " + job_id + "; exit 1;", 
stdout=subprocess.PIPE, stderr=subprocess.PIPE, shell=True)

while p.poll() is None:
    err = p.stderr.readline().decode('utf_8')
    out = p.stdout.readline().decode('utf_8')
    if "changed" in err or "changed" in out:
        subprocess.Popen("echo rescheduling was successful!", shell=True)
os._exit(0)

我阅读了一些文档,open3 函数可能在这里工作,但对于 p.poll() 部分,我不确定该使用什么。

4

1 回答 1

3

答案取决于在打印行之后(仍在运行时)"rescheduling was successful!" 立即打印消息是否重要,或者在退出后打印该行是否足够。bmodbmodbmod

最后一种情况在 Perl 中很容易实现,例如:

my $out = qx/bmod -b $beginTime $job_id 2>&1/;
say "rescheduling was successful!" if $out =~ /changed/;

关于第一种情况,如果您需要立即打印消息(甚至在bmod退出之前),请首先注意您的 Python 脚本可能无法正常工作。这些p.stderr.readline()行将阻塞脚本,直到准备好从中读取一行p.stderr,类似地,p.stdout.readline()将阻塞脚本,直到准备好从中读取一行p.stdout。因此,如果bmod只打印到stdout而没有任何内容到stderr,脚本将在第一次调用时挂起p.stderr.readline()并且仅在bmod退出时返回。

我不确定如何在 Python 中正确执行此操作,但在 Perl 中,您可以IPC::Open3结合使用IO::Select. 例如:Perl select return “bad file descriptor” 错误

另请注意:Perl 中更简单的解决方案可以使用openifstderrstdoutare 来实现:

my $pid = open ( my $fh, '-|', "bmod -b $beginTime $job_id 2>&1" ) or die "Could not run command: $!";
while ( my $line = <$fh> ) {
     print $line if $line =~ /changed/;
}
close $fh;
于 2016-05-11T18:18:06.413 回答