from threading import Thread
import time
print 'start of script'
class MyThread(Thread):
def run(self):
for i in xrange(10):
print 'thread->', '['+self.name+']', '('+str(i)+')'
time.sleep(2)
for i in range(3):
my_thread = MyThread()
my_thread.name = i
my_thread.start()
print 'end of script'
>>> ================================ RESTART ================================
>>>
start of script
thread->thread->thread->end of script
[0][1][2]
>>> (0)(0)(0)
thread->thread->thread-> [0][2][1] (1)(1)(1)
thread->thread-> thread-> [0] [2] [1] (2) (2)
(2)
thread-> thread->thread->[0] [2][1](3)
(3)(3)
thread-> thread->thread->[0] [2][1](4)
(4)(4)
thread-> thread->[0]thread-> [2](5)[1]
(5)(5)
thread-> [0]thread->thread-> (6)[2][1]
(6)(6)
thread-> thread->[0]thread-> [2](7)[1]
(7)(7)
thread-> thread->[0] thread-> [2] (8) [1]
(8)
(8)
thread->thread-> thread-> [0] [2] [1] (9) (9)
(9)
>>>
正如你所看到我首先打印'脚本开头',然后执行多个线程,然后打印'脚本结束'
然而,在我执行第一个线程之后,“脚本结束”被立即打印,而不是在所有线程完成之后。我该如何防止这种情况?
输出的混乱性质是预期的,实际上是期望的,因为这些线程应该同时执行...
我在Windows 7 python 2.7顺便说一句......
答案 0 :(得分:7)
这是完全正常的。您不是在等待线程完成,因此在for
循环后您的代码没有理由阻止。
如果你想等待它们,你需要在第二个循环中在每个线程上调用.join()
。
然而,在我执行第一个线程之后,“脚本结束”被立即打印,而不是在所有线程完成之后
这只是你得到的印象。运行该代码几百次,您可以在任何线程输出之前或者在记录了两个或三个线程之后看到“脚本结束”。 一旦所有线程都已启动,就会打印出“脚本结束”。
一旦你启动一个线程,它就会与其他资源(包括你的主线程)竞争CPU等资源。运行哪个线程由操作系统决定,并且(通常)不在您的控制之下,也不可预测。
所以在你发布的输出中,第一个线程获得了一点CPU,而主线程仍在忙着启动其他线程。那只是一个“巧合”。
答案 1 :(得分:5)
您想要添加.join()
,因为默认情况下,在线程完成之前,您的主程序没有理由阻止:
my_threads = []
for i in range(3):
my_thread = MyThread()
my_thread.name = i
my_thread.start()
my_threads.append(my_thread)
for t in my_threads:
t.join()
print 'end of script'
答案 2 :(得分:1)
跟踪线程对象,并在打印join()
之前调用对象上的end of script
以等待线程完成。