下面是探索出来的一种比较安全简易的方法。
import time
from concurrent.futures.process import ProcessPoolExecutor
from concurrent.futures.thread import ThreadPoolExecutor
from multiprocessing import Manager
from multiprocessing.managers import SyncManager
from queue import PriorityQueue
_sentinel = None
class MyManager(SyncManager):
pass
MyManager.register("PriorityQueue", PriorityQueue)
def Manager():
m = MyManager()
m.start()
return m
class MyClass:
def thread_func(self, item, q1, q2):
print('item: {} in thread'.format(item))
q1.put(Exception("test exception"))
def _process(self, q0, q1, q2):
thread_pool = ThreadPoolExecutor(2)
while True:
if not q0.empty():
item = q0.get()
if item == _sentinel:
q0.put(_sentinel)
print("receive sentinel, over process")
break
thread_pool.submit(self.thread_func, item, q1, q2)
else:
time.sleep(1)
def run(self):
process_pool = ProcessPoolExecutor(2)
process_rets = []
q0 = Manager().Queue(maxsize=4)
q1 = Manager().Queue(maxsize=4)
q2 = Manager().PriorityQueue(4)
for i in range(2):
process_rets.append(process_pool.submit(self._process, q0, q1, q2))
q0.put(11)
q0.put(22)
q0.put(33)
q0.put(44)
q0.put(_sentinel)
q2.put(2)
q2.put(1)
q2.put(4)
q2.put(3)
for ret in process_rets:
ret.result()
print('q length:', q1.qsize())
# while not q.empty(): # q.get().result() print(q2.get())
if __name__ == "__main__":
obj = MyClass()
obj.run()