psutil中没有运行的进程、重用的进程或已死的僵尸进程

4 投票
2 回答
6959 浏览
提问于 2025-04-18 00:50

psutil.process_iter()包含了什么内容呢?因为它是一个缓存的实例,所以它只包括当前正在运行的进程,还是说包括所有进程,只是让用户自己去确认它们的当前状态?我的代码:

for _process in psutil.process_iter():
    try:
        new_proc = _process.as_dict(attrs=['cpu_times', 'name', 'pid', 'status'])
    except psutil.NoSuchProcess:
        continue

这里过滤掉了哪些状态?还有哪些我需要自己去确认的呢?

2 个回答

2

psutil.process_iter() 是一个用来遍历系统中所有正在运行的进程的函数。ZombieProcess 错误通常出现在 MacOS 系统中,解决这个问题的一种方法是在代码中处理这个异常,也就是用 except psutil.ZombieProcess: 来捕捉这个错误。

for _process in psutil.process_iter():
    try:
        new_proc = _process.as_dict(attrs=['cpu_times', 'name', 'pid', 'status'])
    except psutil.NoSuchProcess:
        continue
    except psutil.ZombieProcess:
        continue
1

关于 psutil.process_iter() 的文档说

这个方法会返回一个迭代器,它会为本地机器上所有正在运行的进程生成一个 Process 类的实例。每个实例只会创建一次,然后会被存储在一个内部表中,每次返回一个元素时,这个表都会更新强调是我自己的

这里的“正在运行”是通过.is_running() 方法来定义的,这个方法对于僵尸进程会返回 True。即使进程已经消失并且它的 pid 被重新使用,.is_running() 也是安全的。

我的理解是,当 psutil.process_iter() 返回 _process 时,_process.is_running() 是真的。从原则上讲,在 _process.as_dict 返回信息之前,可能会发生几种情况:

  1. 进程可能会死掉——变成僵尸:此时 _process.is_running() 是真的,pidstatus 是有意义的。
  2. 它可能被回收——彻底死掉:此时进程信息不可用(会抛出 psutil.NoSuchProcess 异常)或者信息过时(如果是缓存的)。
  3. 它的 pid 可能被重新使用——某些 _process 方法可能会错误地返回新进程的信息。.is_running() 使用了多个进程属性,所以应该能检测到 pid 被重新使用的情况。

通常情况下,操作系统不会立即重新使用 pid,所以第三种情况不应该经常发生。

撰写回答