当前位置: 首页 > 面试题库 >

一旦其中一个工人满足特定条件,终止Python多处理程序

商松
2023-03-14
问题内容

我正在使用其多处理模块编写Python程序。该程序调用许多辅助函数,每个辅助函数产生一个随机数。
一旦其中一名工人生产的数值大于0.7,我就需要终止程序

下面是我的程序,其中“ 如何执行 ”部分尚未填写。任何想法?谢谢。

import time
import numpy as np
import multiprocessing as mp
import time
import sys

def f(i):
    np.random.seed(int(time.time()+i))

    time.sleep(3)
    res=np.random.rand()
    print "From i = ",i, "       res = ",res
    if res>0.7:
        print "find it"
        # terminate  ???? Question: How to do this???


if __name__=='__main__':
    num_workers=mp.cpu_count()
    pool=mp.Pool(num_workers)
    for i in range(num_workers):
        p=mp.Process(target=f,args=(i,))
        p.start()

问题答案:

os.kill()像大锤一样,没有任何方法可以阻止其他短小的暴力。不要去那

为了明智地做到这一点,您需要重新设计基本方法:主流程和工作流程需要相互通信。

我会充实它,但是到目前为止,该示例
简单了,无法使用。例如,按照书面规定,最多num_workers只能rand()进行调用,因此没有理由相信其中任何一个必须大于0.7。

一旦worker函数增长了一个循环,它就会变得更加明显。例如,工作人员可以检查mp.Event循环顶部是否设置了,如果退出则直接退出。主要过程将设置Event希望工人停止的时间。

当工人mp.Event发现值>
0.7时,可以设置一个不同的值。主要过程将等待该事件Event,然后设置“停止时间”Event以供工作人员查看,然后执行通常的循环-.join()使工作人员彻底关闭。

假设工人要继续努力,直到至少有人发现一个值>
0.7,这才是一种充实,干净的解决方案。请注意,我已将其删除numpy,因为它与这段代码无关。在任何支持multiprocessing以下平台的库存Python下,此处的代码都可以正常工作:

import random
from time import sleep

def worker(i, quit, foundit):
    print "%d started" % i
    while not quit.is_set():
        x = random.random()
        if x > 0.7:
            print '%d found %g' % (i, x)
            foundit.set()
            break
        sleep(0.1)
    print "%d is done" % i

if __name__ == "__main__":
    import multiprocessing as mp
    quit = mp.Event()
    foundit = mp.Event()
    for i in range(mp.cpu_count()):
        p = mp.Process(target=worker, args=(i, quit, foundit))
        p.start()
    foundit.wait()
    quit.set()

和一些示例输出:

0 started
1 started
2 started
2 found 0.922803
2 is done
3 started
3 is done
4 started
4 is done
5 started
5 is done
6 started
6 is done
7 started
7 is done
0 is done
1 is done

一切都彻底关闭:没有回溯,没有异常终止,没有留下僵尸进程……像哨子一样干净。

杀了它

正如@noxdafox所指出的,有一种Pool.terminate()方法可以在所有平台上尽其所能来杀死工作进程,无论它们在做什么(例如,在Windows上称为平台TerminateProcess())。我不建议将其用于生产代码,因为突然终止进程可能会使各种共享资源处于不一致状态,或者使它们泄漏。在multiprocessing文档中有关于此的各种警告,您应该在其中添加OS文档。

不过,这可能很方便!这是使用此方法的完整程序。请注意,我将临界值提高到0.95,以使其花费的时间比眨眼的时间更长:

import random
from time import sleep

def worker(i):
    print "%d started" % i
    while True:
        x = random.random()
        print '%d found %g' % (i, x)
        if x > 0.95:
            return x # triggers callback
        sleep(0.5)

# callback running only in __main__
def quit(arg):
    print "quitting with %g" % arg
    # note: p is visible because it's global in __main__
    p.terminate()  # kill all pool workers

if __name__ == "__main__":
    import multiprocessing as mp
    ncpu = mp.cpu_count()
    p = mp.Pool(ncpu)
    for i in range(ncpu):
        p.apply_async(worker, args=(i,), callback=quit)
    p.close()
    p.join()

和一些示例输出:

$ python mptest.py
0 started
0 found 0.391351
1 started
1 found 0.767374
2 started
2 found 0.110969
3 started
3 found 0.611442
4 started
4 found 0.790782
5 started
5 found 0.554611
6 started
6 found 0.0483844
7 started
7 found 0.862496
0 found 0.27175
1 found 0.0398836
2 found 0.884015
3 found 0.988702
quitting with 0.988702
4 found 0.909178
5 found 0.336805
6 found 0.961192
7 found 0.912875
$ [the program ended]


 类似资料:
  • 问题内容: 我正在学习如何使用Python多处理库。但是,当我浏览一些示例时,最终我在后台运行了许多python进程。 其中的例子看起来象下面这样: 现在,这是我的“ TOP”命令的屏幕截图: 我不知道如何一口气杀死他们。 ps … | grep python ....杀死吗? 我需要添加哪种python代码,以避免再次发生这种悲惨的情况。谢谢! 问题答案: 您需要在工作队列中处理您的进程,该进程

  • 我正处于Java的学习阶段。我想用Java编写一个程序,它可以读取一个Excel文件(.xlsx)。此文件有一些列和许多行。我想将数据写入另一个Excel文件(.xlsx),仅满足条件,而不是现有文件中的所有数据。 我的Excel工作表如下所示 我想只过滤那些带有代理Edelweiss的行,并把它放在另一个Excel表中。我知道如何使用Java将一个Excel中的所有数据复制到另一个Excel中。

  • 问题内容: 我将不胜感激创建此查询的任何帮助。我尝试了好几种方法,但都没有碰到运气。由于我的问题很难表达,因此我将举一个我想做的简单例子。我的数据在结构上类似于以下内容: 如果我有两种特定颜色的ID,我想创建一个查询以返回类型。例如,我想查找所有具有蓝色和红色的ID。然后查询将返回: A和B的返回顺序并不重要。数据集很大,我希望有许多ID可以同时满足这两个条件(也许是50,000个左右)。我要指出

  • 问题内容: 使用以下模型: 如果我要查找包含至少一篇文章的订单操作,则可以按预期工作: 但是,如果要查找订单中所有商品的订单操作,正确的方法是什么? 引发错误(我理解为什么会这样)。 问题答案: 一个简单的解决方案: 这只是一个查询,但每篇文章都有一个内部联接。对于多篇文章,Willem更巧妙的解决方案应该会表现更好。

  • 我有一个迷宫,我必须用递归来解。迷宫必须在找到开放路径的地方放置一个X(我的代码就是这样做的)。它必须这样做,直到使用递归调用到达出口为止(我的代码就是这样做的,下面描述的除外)。它还必须在到达死胡同的地方放置一个O,将操作系统拉回到“正确”路径,然后沿着新路径继续求解(我的代码就是这样做的)。 然而,一旦到达迷宫的末端,它就必须求解一个新的迷宫(原始迷宫,转置)。我的问题如下: 一旦我到达迷宫的

  • 我在页面上有输入字段和提交按钮。 这里是jQuery代码: 我想防止模糊,如果从输入字段点击提交div,但想允许它,如果从输入字段点击页面的其他部分。我无法使用“提交”按钮。 我已竖起了小提琴。净/405kzboh/1 但是现在我甚至不明白为什么点击事件没有在模糊事件之前触发,如果有人从输入点击提交!