在python中使用multiprocessing.Process类时,是否有办法记录给定Process的stdout输出?
Answers:
最简单的方法可能是覆盖sys.stdout
。从多处理手册中稍微修改一个示例:
from multiprocessing import Process
import os
import sys
def info(title):
print title
print 'module name:', __name__
print 'parent process:', os.getppid()
print 'process id:', os.getpid()
def f(name):
sys.stdout = open(str(os.getpid()) + ".out", "w")
info('function f')
print 'hello', name
if __name__ == '__main__':
p = Process(target=f, args=('bob',))
p.start()
q = Process(target=f, args=('fred',))
q.start()
p.join()
q.join()
并运行它:
$ ls py $ python m.py $ ls 27493.out 27494.out m.py $ cat 27493.out 函数f 模块名称:__ main__ 父进程:27492 进程编号:27493 你好鲍勃 $ cat 27494.out 函数f 模块名称:__ main__ 父进程:27492 进程编号:27494 你好弗雷德
我只会在@Mark Rushakoff答案中添加两件事。调试时,我发现将调用的buffering
参数更改open()
为0确实很有用。
sys.stdout = open(str(os.getpid()) + ".out", "a", buffering=0)
否则为madness,因为在tail -f
输出文件时,结果可能会断断续续。buffering=0
为tail -f
伟大。
为了完整起见,请帮自己一个忙,并重定向sys.stderr
。
sys.stderr = open(str(os.getpid()) + "_error.out", "a", buffering=0)
另外,为方便起见,您可以根据需要将其转储到单独的流程类中,
class MyProc(Process):
def run(self):
# Define the logging in run(), MyProc's entry function when it is .start()-ed
# p = MyProc()
# p.start()
self.initialize_logging()
print 'Now output is captured.'
# Now do stuff...
def initialize_logging(self):
sys.stdout = open(str(os.getpid()) + ".out", "a", buffering=0)
sys.stderr = open(str(os.getpid()) + "_error.out", "a", buffering=0)
print 'stdout initialized'
这是捕获stdout以便进行multiprocessing.Process和io.TextIOWrapper的简单 明了:
import app
import io
import sys
from multiprocessing import Process
def run_app(some_param):
out_file = open(sys.stdout.fileno(), 'wb', 0)
sys.stdout = io.TextIOWrapper(out_file, write_through=True)
app.run()
app_process = Process(target=run_app, args=('some_param',))
app_process.start()
# Use app_process.termninate() for python <= 3.7.
app_process.kill()