【问题标题】:Running a Python Subprocess运行 Python 子进程
【发布时间】:2011-06-27 18:36:27
【问题描述】:

全部,

我已经阅读了几个关于如何在 python 中运行子进程的线程,但似乎没有一个对我有帮助。这可能是因为我不知道如何正确使用它们。我有几种方法我想同时运行而不是按顺序运行,我认为 subprocess 模块会为我执行此操作。

def services():
     services = [method1(),
            method2(),
            method3(),  
            mrthod4(),
            method5()]
     return services

def runAll():
    import subprocess
    for i in services():
        proc = subprocess.call(i,shell=True)

这种方法的问题是 method1() 启动,而 method2() 直到 1 完成才启动。我尝试了几种方法,包括在我的服务方法中使用 subprocess.Popen[] 都没有运气。谁能帮我看看如何让方法 1-5 同时运行?

谢谢, 亚当

【问题讨论】:

    标签: python subprocess


    【解决方案1】:

    根据 Python 文档,subprocess.call() 等待命令完成。您应该直接使用 subprocess.Popen 对象,这将为您提供所需的灵活性。

    【讨论】:

      【解决方案2】:

      在 python 3.2.x 中,并发期货模块使这类事情变得非常容易。

      【讨论】:

        【解决方案3】:

        【讨论】:

        • 线程可能根本不合适,除非任务受 I/O 限制或 OP 正在运行 Jython。多处理是一个更好的主意。
        【解决方案4】:

        通过说method1(),您正在调用该函数并等待它返回。 (这是一个函数,而不是一个方法。)

        如果你只是想并行运行一堆重载函数并收集它们的结果,你可以使用joblib

        from joblib import Parallel, delayed
        
        functions = [fn1, fn2, fn3, fn4]
        
        results = Parallel(n_jobs=4)(delayed(f)() for f in functions)
        

        【讨论】:

          【解决方案5】:

          subprocess.call() 阻塞,直到进程完成。

          multiprocessing 听起来更适合你的工作。

          例如:

          from multiprocessing import Process
          
          def f1():
              while True:
                  print 'foo'
          
          def f2():
              while True:
                  print 'bar'
          
          def f3():
              while True:
                  print 'baz'
          
          if __name__ == '__main__':
              for func in (f1, f2, f3):
                  Process(target=func).start()
          

          【讨论】:

            【解决方案6】:

            您需要使用 & 来异步执行它们。这是一个例子:

             subprocess.call("./foo1&", shell=True)
             subprocess.call("./foo2&", shell=True)
            

            这就像普通的 unix shell。

            编辑:尽管有多种更好的方法可以做到这一点。有关一些示例,请参见其他答案。

            【讨论】:

              【解决方案7】:

              subprocess 不会使进程异步。您想要实现的目标可以使用多线程或多处理模块来完成。

              【讨论】:

                【解决方案8】:

                我最近遇到了类似的问题,是这样解决的:

                from multiprocessing import Pool
                def parallelfuncs(funcs, args, results, bad_value = None):
                    p = Pool()
                    waiters = []
                    for f in funcs:
                        waiters.append(p.apply_async(f, args, callback = results.append))
                    p.close()
                    for w in waiters:
                        if w.get()[0] == bad_value:
                            p.terminate()
                    return p
                

                好消息是函数 funcs 在 args 上并行执行(类似于 map 的反转),并返回结果。多处理池使用所有处理器并处理作业执行。

                w.get 块,如果不清楚的话。

                对于您的用例,您可以调用

                results = []
                parallelfuncs(services, args, results).join()
                print results
                

                【讨论】:

                  猜你喜欢
                  • 1970-01-01
                  • 2022-01-06
                  • 2020-06-16
                  • 2013-05-03
                  • 2014-10-11
                  • 2017-12-21
                  • 1970-01-01
                  • 1970-01-01
                  • 2022-07-27
                  相关资源
                  最近更新 更多