我从StackOverflow的几篇文章中获取了灵感编写了以下代码。
场景
我想要创建一个多进程队列,在该队列上有多个工作进程“监听”。
在接收到键盘中断的情况下,主进程不再向队列中加入新的项目,并且利用哨兵对象来优雅地停止工作进程。
问题
我目前使用的版本存在以下问题:
signal.signal(signal.SIGINT, signal.SIG_IGN)
忽略Ctrl + C的同时也忽略主进程。
有什么想法吗?我需要使用多进程工作池吗?一些示例表明我可能需要。那我还能用队列吗?
from multiprocessing import Pool, Process,Queue
import time
import signal
# http://docs.python.org/3.1/library/multiprocessing.html#multiprocessing.Queue
# http://docs.python.org/3.1/library/multiprocessing.html#multiprocessing.Process
class Worker(Process):
def __init__(self, queue,ident):
super(Worker, self).__init__()
# Ignore Signals
signal.signal(signal.SIGINT, signal.SIG_IGN)
self.queue= queue
self.idstr= str(ident)
print "Ident" + self.idstr
def run(self):
print 'Worker started'
# do some initialization here
print 'Computing things!'
for data in iter( self.queue.get, None ):
print "#" + self.idstr + " : " + str(data)
time.sleep(5)
print "#" + self.idstr + "Queue Size: " + str(self.queue.qsize())
print "Worker Done"
#### Main ####
request_queue = Queue(10)
for i in range(4):
Worker( request_queue,i ).start()
try:
for data in range(1000000):
request_queue.put( data )
#print "Queue Size: " + str(request_queue.qsize())
# Sentinel objects to allow clean shutdown: 1 per worker.
for i in range(4):
request_queue.put( None )
except KeyboardInterrupt:
print "Caught KeyboardInterrupt, terminating workers"
while request_queue.empty()==False:
request_queue.get()
request_queue.put( None )