python - Thread.join() 在 python 中到底做了什么?这是对 Thread.join() 的错误使用吗?
问题描述
我最近开始学习如何在 python 中编写多线程程序,对于初学者来说,开始在不使用队列的情况下进行实验。
在下面的代码中,loadFunction 只是线程的一个示例目标函数。它应该等到等待(列表)参数中提供的所有线程都完成执行(我正在尝试使用 join() 来实现这一点)。然后开始打印指定的数字范围。这是期望的行为。
在主程序中,我创建了两个线程,它们不等待任何其他线程开始计数。然后我创建了第三个线程,它应该在开始计数之前等待前两个线程完成执行。
然而,这并没有发生。在测试中,我发现三个线程同时开始执行,而第三个线程并没有像我预期的那样等待前两个线程完成执行。
所以我的问题是,我缺少关于 Thread.join() 函数的哪些知识,以及我可以对我的代码进行哪些更改以达到预期的结果?
代码:
""" Note: Python 3.3 onwards required since daemon was added as an initializable
property from python 3.3 onwards."""
import threading
def loadFunction(name, start, end, wait=[]):
""" wait should be a list of threads to wait for """
map(lambda th: th.join(), wait)
for number in range(start, end):
print("%s : %d" % (name, number))
if __name__ == "__main__":
t1 = threading.Thread(target=loadFunction, args=("Thread1", 1, 101), name="Thread1" ,daemon=True)
t2 = threading.Thread(target=loadFunction, args=("Thread2", 101, 201), name="Thread2", daemon=True)
t3 = threading.Thread(target=loadFunction, args=("Thread3", 1000, 1101, [t1, t2]), name="Thread3", daemon=True)
t1.start()
t2.start()
t3.start()
# wait for all of the daemon processes to finish before we close the program
t1.join()
t2.join()
t3.join()
print("done!")
结果的一部分(一次运行):
Thread1 : 1
Thread1 : 2
Thread1 : 3
Thread1 : 4
Thread1 : 5
Thread1 : 6
Thread2 : 101
Thread2 : 102
Thread2 : 103
Thread2 : 104
Thread2 : 105
Thread2 : 106
Thread2 : 107
Thread2 : 108
Thread2 : 109
Thread1 : 7
Thread1 : 8
Thread1 : 9
Thread1 : 10
Thread1 : 11
Thread3 : 1000
Thread1 : 12
Thread1 : 13
Thread3 : 1001
Thread1 : 14
Thread3 : 1002
Thread1 : 15
Thread3 : 1003
Thread1 : 16
Thread2 : 110
这是我在编写这段代码时想到的两件事(引用自官方文档):
加入(超时=无)
等到线程终止。这会阻塞调用线程,直到调用其 join() 方法的线程终止...
参考我的示例代码,“调用线程”会是调用 loadFunction 函数的线程吗?我有点怀疑情况并非如此,并且进程本身调用了函数而不是线程,因此线程不会是等待的线程,而是进程等待。如果是这种情况,我将如何解决它?我有一种感觉会涉及到排队……如果这首先是原因的话。
和:
一个线程可以被 join() 多次。
是什么导致我两次将 join 用于同一线程。
PS 我第一次在 python 中学习线程,但这是在学习 C 中的分叉过程之后,所以我可能会因此而在这里感到困惑。如果两者不相关,那么我很抱歉,我的印象是两者是相似的(尽管显然不一样,因为一个拆分进程,而另一个在进程本身内创建线程)。
谢谢你。
解决方案
“调用线程”会是调用 loadFunction 函数的线程吗?
调用线程是调用的线程join
。so t1.join()
and t2.join()
andt3.join()
导致主线程阻塞,如果没有延迟评估,内部的连接loadFunction
会导致 t3 阻塞。map
我将如何解决它?
您内部loadFunction
的连接没有执行,因为map
在您迭代它之前不会执行任何代码。正如 MaxNoe 建议的那样,您应该改用普通的 for 循环。
def loadFunction(name, start, end, wait=[]):
""" wait should be a list of threads to wait for """
for t in wait:
t.join()
for number in range(start, end):
print("%s : %d" % (name, number))
推荐阅读
- python - NoneType' object has no attribute 'all
- lua - Is there an easy way to get all global variables defined in a Lua code file?
- java - 即使数组不是回文,回文练习也会返回 true?
- laravel - 在所有 Vue.js 组件之间共享数据
- mongodb - 更改 MongoDb 中许多文档的字段类型
- python - 跨多个 DataFrame 重命名索引
- python - 当 dict 中的值是列表时,如何对 dict 进行这种拆分?
- android - 将 configChanges 应用到每个活动或以编程方式应用它?
- nuxt.js - 将 Nuxt 中的索引设置到其他位置
- firebase - Firebase 中“session_start”的“session_engaged”事件属性是什么?