perl后台进程

perl后台进程,perl,background,fork,sleep,wait,Perl,Background,Fork,Sleep,Wait,我正在尝试用perl运行一个后台进程。我创建了一个子进程,用于调用另一个perl脚本。我想与这个子进程并行运行几行代码。在子进程完成后,我想打印一行代码 主脚本 testing.pl 预期产量 在子进程之前 等待前命令 (应等待20秒,然后打印) 等待20秒后,读取数据的时间 您可以在后台使用以下命令运行命令: system("cmd &"); 命令的STDOUT和STDERR(可能还有STDIN,具体取决于shell)将与父命令相同。您不需要捕捉SIGCHLD,因

我正在尝试用perl运行一个后台进程。我创建了一个子进程,用于调用另一个perl脚本。我想与这个子进程并行运行几行代码。在子进程完成后,我想打印一行代码

主脚本 testing.pl 预期产量 在子进程之前 等待前命令 (应等待20秒,然后打印) 等待20秒后,读取数据的时间

您可以在后台使用以下命令运行命令:

system("cmd &");
命令的
STDOUT
STDERR
(可能还有
STDIN
,具体取决于shell)将与父命令相同。您不需要捕捉
SIGCHLD
,因为发生了双叉
fork
;详情见下文

在程序中的
系统
的参数中添加一个符号可以大大简化主程序

#! /usr/bin/env perl

print "before the child process\n";

system("perl testing.pl &") == 0
  or die "$0: perl exited " . ($? >> 8);

print "before wait command\n";

wait;
die "$0: wait: $!" if $? == -1;

print "after 20 secs of waiting\n";

你的脚本有很多问题。始终:

use strict;
use warnings;
local
ising特殊变量是一种很好的做法。只有包含特殊值
unde
的变量才会为定义的
返回false。因此,对于定义的
值,每一个其他值(即使是
0
;这里就是这种情况)都返回true。在另一个脚本中,该脚本是错误的

#!/usr/bin/perl

use strict;
use warnings;

local $| = 1;

print "Before the child process\n";

unless (fork) {
    system("perl testing.pl");
    exit;
}

print "Before wait command\n";
wait;
print "After 20 secs of waiting\n";

fork
返回值处理确实有点棘手。 具有一个漂亮而简洁的分叉习惯用法,在您的例子中,它如下所示:

#!/usr/bin/env perl
use 5.010000;
use strict;
use warnings qw(all);

say 'before the child process';
given (fork) {
    when (undef) { die "couldn't fork: $!" }
    when (0) {
        exec $^X => 'testing.pl';
    } default {
        my $pid = $_;
        say 'before wait command';
        waitpid $pid, 0;
        say 'after 20 secs of waiting';
    }
}

请注意
exec$^X=>“…”
行:$^X变量保存当前Perl可执行文件的完整路径,因此将保证“正确的Perl版本”。另外,
system
调用在您进行预分叉时是毫无意义的。

那么您看到的是什么呢?值得注意的是,
系统
调用之后的所有内容都将由父进程和子进程执行。。它正在打印两次。我该如何控制它呢?:这是因为
0
是Perl中定义的
值。删除了您在编辑中添加的bug。@AlanHaggaiAlavi即使修复了bug,在父级和子级中执行后的代码,因为
if
分支不包含
exit
。我错误地错过了这一部分,我已经把它包括在报告中了code@dreamer,格雷格·培根建议,作为使用
fork
的替代方法。
use strict;
use warnings;
#!/usr/bin/perl

use strict;
use warnings;

local $| = 1;

print "Before the child process\n";

unless (fork) {
    system("perl testing.pl");
    exit;
}

print "Before wait command\n";
wait;
print "After 20 secs of waiting\n";
#!/usr/bin/env perl
use 5.010000;
use strict;
use warnings qw(all);

say 'before the child process';
given (fork) {
    when (undef) { die "couldn't fork: $!" }
    when (0) {
        exec $^X => 'testing.pl';
    } default {
        my $pid = $_;
        say 'before wait command';
        waitpid $pid, 0;
        say 'after 20 secs of waiting';
    }
}