鍵盤(pán)中斷python的多處理池如何使用python的多處理池處理KeyboardInterrupt事件?這是一個(gè)簡(jiǎn)單的例子:from multiprocessing import Poolfrom time import sleepfrom sys import exitdef slowly_square(i):
sleep(1)
return i*idef go():
pool = Pool(8)
try:
results = pool.map(slowly_square, range(40))
except KeyboardInterrupt:
# **** THIS PART NEVER EXECUTES. ****
pool.terminate()
print "You cancelled the program!"
sys.exit(1)
print "\nFinally, here are the results: ", resultsif __name__ == "__main__":
go()當(dāng)運(yùn)行上面的代碼時(shí),KeyboardInterrupt當(dāng)我按下時(shí)會(huì)引發(fā)上升^C,但是該過(guò)程只是掛起,我必須在外部殺死它。我希望能夠隨時(shí)按下^C并使所有進(jìn)程正常退出。
3 回答

繁華開(kāi)滿天機(jī)
TA貢獻(xiàn)1816條經(jīng)驗(yàn) 獲得超4個(gè)贊
這是一個(gè)Python bug。在等待threading.Condition.wait()中的條件時(shí),從不發(fā)送KeyboardInterrupt。攝制:
import threading cond = threading.Condition(threading.Lock())cond.acquire()cond.wait(None)print "done"
在wait()返回之前,不會(huì)傳遞KeyboardInterrupt異常,并且它永遠(yuǎn)不會(huì)返回,因此中斷永遠(yuǎn)不會(huì)發(fā)生。KeyboardInterrupt幾乎肯定會(huì)中斷條件等待。
請(qǐng)注意,如果指定了超時(shí),則不會(huì)發(fā)生這種情況; cond.wait(1)將立即收到中斷。因此,解決方法是指定超時(shí)。要做到這一點(diǎn),請(qǐng)更換
results = pool.map(slowly_square, range(40))
同
results = pool.map_async(slowly_square, range(40)).get(9999999)
或類似的。

函數(shù)式編程
TA貢獻(xiàn)1807條經(jīng)驗(yàn) 獲得超9個(gè)贊
由于某些原因,只能Exception
正常處理從基類繼承的異常。作為一種解決方法,您可以重新提升您KeyboardInterrupt
的Exception
實(shí)例:
from multiprocessing import Poolimport timeclass KeyboardInterruptError(Exception): passdef f(x): try: time.sleep(x) return x except KeyboardInterrupt: raise KeyboardInterruptError()def main(): p = Pool(processes=4) try: print 'starting the pool map' print p.map(f, range(10)) p.close() print 'pool map complete' except KeyboardInterrupt: print 'got ^C while pool mapping, terminating the pool' p.terminate() print 'pool is terminated' except Exception, e: print 'got exception: %r, terminating the pool' % (e,) p.terminate() print 'pool is terminated' finally: print 'joining pool processes' p.join() print 'join complete' print 'the end'if __name__ == '__main__': main()
通常你會(huì)得到以下輸出:
staring the pool map[0, 1, 2, 3, 4, 5, 6, 7, 8, 9]pool map complete joining pool processes join complete the end
所以,如果你點(diǎn)擊^C
,你會(huì)得到:
staring the pool map got ^C while pool mapping, terminating the pool pool is terminated joining pool processes join complete the end
添加回答
舉報(bào)
0/150
提交
取消