在python中运行多线程被挂起

时间:2019-01-03 07:51:10

标签: python multithreading

我在python中测试多线程,但是代码被挂起:

class MongoInsertThread(threading.Thread):
    def __init__(self,  queue, thread_id):
        super(MongoInsertThread, self).__init__()
        self.thread_id = thread_id
        self.queue = queue

    def run(self):
        print(self.thread_id,': ', self.queue.get())

def save_to_mongo_with_thread():
    q = queue.Queue()
    size = int(math.ceil(16 / 3))

    for e in range(size):
        for i in range(e * size, min((e + 1) * size, 16)):
            q.put([i], block=False)
        threads = []
        for i in range(size):
            threads.append(MongoInsertThread(q, i))
        for t in threads:
            t.start()
        for t in threads:
            t.join()
        print("+++++++++++++++++++++++")

结果是我想要的,但是程序没有结束,结果是:

0 :  [0]
1 :  [1]
2 :  [2]
3 :  [3]
4 :  [4]
5 :  [5]
+++++++++++++++++++++++
0 :  [6]
1 :  [7]
2 :  [8]
3 :  [9]
4 :  [10]
5 :  [11]
+++++++++++++++++++++++
0 :  [12]
1 :  [13]
2 :  [14]
3 :  [15]

但是它不能打印最后的+++++++++++++++++++++++,我该如何处理?

1 个答案:

答案 0 :(得分:1)

您拨打q.put() 16次-每产生i in range(e * 5, (e + 1)*5)的{​​{1}}

  1. e in range(5)
  2. i in range(0, 5)
  3. i in range(5, 10)
  4. i in range(10, 15)
  5. i in range(15, 16)
  6. i in range(20, 16)

i in range(25, 16)值附加到16。但是,您创建了q线程,并带有对25的关联25调用-但是一旦删除了第一个q.get()元素,就会16个块。如果您使用get(),代码将成功完成,但是您会收到许多警告,提示您从q.get(block=False)发出Empty。更改循环的循环条件

get()

for i in range(size): threads.append(MongoInsertThread(q, i))

将解决不匹配问题。但是,在添加和删除所有range(e * size, min((e + 1) * size, 16))元素之后,添加break语句以停止最外面的for循环也很有用。

完整示例

16

输出-

class MongoInsertThread(threading.Thread):
    def __init__(self,  queue, thread_id):
        super(MongoInsertThread, self).__init__()
        self.thread_id = thread_id
        self.queue = queue

    def run(self):
        print(self.thread_id,': ', self.queue.get(block=False))

def save_to_mongo_with_thread():
    q = Queue.Queue()
    size = int(math.ceil(16 / 3))
    for e in range(5):
        if (e*size > 16): 
            break
        for i in range(e * size, min((e + 1) * size, 16)):
            q.put([i], block=False)
        threads = []
        for i in range(e * size, min((e + 1) * size, 16)):
            threads.append(MongoInsertThread(q, i))
        for t in threads:
            t.start()
        for t in threads:
            t.join()
        print("+++++++++++++++++++++++")

还请注意,我正在使用0: [0] 1: [1] 2: [2] 3: [3] 4: [4] +++++++++++++++++++++++ 5: [5] 6: [6] 7: [7] 8: [8] 9: [9] +++++++++++++++++++++++ 10: [10] 11: [11] 12: [12] 13: [13] 14: [14] +++++++++++++++++++++++ 15: [15] +++++++++++++++++++++++ 来帮助阐明将来的问题,但是对于此示例而言,这是不必要的。