Perl pgrep 返回多个 pid

标签 perl

我有一些像这样的perl代码来获取进程的pid(如果它) 存在。我想知道 pgrep 的返回状态,这样我就可以知道 pid 是否有效。这是代码:

#!/usr/bin/perl -w
my $pid=`pgrep -n -f \"akonadiserver\"`;
print "$? ";
chomp $pid;
print "Output1: $pid\n";
$pid=`pgrep -n -f \"akonadiserver\"`;
my $evalue=${^CHILD_ERROR_NATIVE};
chomp $pid;
print "Output2: $pid, $evalue\n";

但是每当我运行它时,我都会得到以下信息:

0 Output1: 3054
Output2: 3056, 0

再跑一次

0 Output1: 3059
Output2: 3061, 0

但是在系统中:

$ pgrep -n -f akonadiserver
1862

这里看到的几个问题:

1) 返回的 pid 一直在变化,很可能是匹配的 grep 进程本身。

2) 我没有办法确定返回的 pid 是否有效。 $? 没有帮助。

如何检查返回状态以及如何在 Perl 中正确使用 pgrep?

最佳答案

从 Perl 脚本运行 `pgrep -n -f akonadiserver` 相当于从终端运行 sh -c "p​​grep -n -f akonadiserver"

来自perlop :

qx/STRING/:
A string which is (possibly) interpolated and then executed as a system command with /bin/sh or its equivalent.

问题在于,将 -f 选项与 pgrep 一起使用将与用于调用该进程的完整命令行进行匹配。这还将包括当前的 pgrep 命令,因为它的命令行将类似于 sh -c "p​​grep -n -f akonadiserver" ,它将与字符串 "匹配akonadiserver”。由于您还将 -n 标志与 pgrep 一起使用,因此它只会返回与 "akonadiserver" 匹配的最新进程,这很可能是pgrep 命令本身(sh -c "p​​grep -n -f akonadiserver").. 这解释了为什么你得到错误的进程 ID。

但是它没有解释为什么它仍然可以在终端窗口中运行。原因是在终端窗口中,pgrep 命令是使用 bash 而不是 sh 运行的(与 Perl 脚本一样),请参阅此有关差异的更多信息,请询问:Difference between pgrep in sh and bash 。因此,从终端窗口运行 pgrep -f 将不会包含 pgrep 命令本身,因此它将适合您的情况。

要从 Perl 获得可靠的结果,您应该使用 Proc::ProcessTable :

use feature qw(say);
use strict;
use warnings;

use Proc::ProcessTable;

my $pat = "akonadiserver";
my $pt = Proc::ProcessTable->new();
my @tab;
for my $p ( @{$pt->table} ){
    if ($p->cmndline =~ /\Q$pat\E/) {
        push @tab, {pid => $p->pid, start => $p->start};
    }
}

say $_->{pid} for (sort {$b->{start} <=> $a->{start}} @tab);

关于Perl pgrep 返回多个 pid,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/31757322/

相关文章:

regex - 如何最好地使用 Perl Regex::Grammars 进行平衡引用?

perl - 使用 Perlbrew 安装古老的 perls

perl - 如何使用 Perl 通过 TCP 连接发送多个文件?

perl - 如何在Perl中的对齐列中编写文本?

linux - 列与制表符而不是空格对齐

javascript - CGI:如何在 JavaScript 中增加 Perl 变量

xml - 查找单个标签内n个相同的内部标签内容

regex - 从文本文件中获取范围模式中的特定行

javascript - 使用 Perl 将斜体字发布到 twitter

html - 使用 Selenium,如何测试返回 XML 而不是 HTML 的 Web UI?