当主线程运行无限循环时,为什么在不同的线程中导入模块需要很长时间?

时间:2014-03-25 07:47:57

标签: python multithreading python-3.4

我有以下Python代码:

import threading
from datetime import datetime
import time

def f():
    print('---- {:%H:%M:%S}'.format(datetime.now()))
    import http.server
    print('---- {:%H:%M:%S}'.format(datetime.now()))

threading.Thread(target=f).start()

while True:
    pass

当我执行它时,我发现import http.server消耗了大量时间。从下面的输出可以看出,导入需要23秒。

C:\>python foo.py
---- 10:12:03
---- 10:12:26

但是,如果我在无限while循环中稍微睡一觉,导入就会更快。

import threading
from datetime import datetime
import time

def f():
    print('---- {:%H:%M:%S}'.format(datetime.now()))
    import http.server
    print('---- {:%H:%M:%S}'.format(datetime.now()))

threading.Thread(target=f).start()

while True:
    time.sleep(1)

输出:

C:\>python foo.py
---- 10:15:58
---- 10:15:58

我知道join()方法的用法,但我想知道为什么当无限import http.server循环没有睡眠语句时while需要这么长时间在它。

2 个答案:

答案 0 :(得分:3)

CPython使用Global Interpreter Lock来保护解释器上下文。这可以防止线程同时运行。实际上它们都运行在单处理器核心上。在CPython中,当线程执行空闲操作(即等待I.O.)时,您可以从线程中受益。或者听插座 你为主线程做了很多工作。虽然pass没有任何意义,它会消耗CPU周期,而且解释器认为给这个线程提供CPU时间很重要。
使用sleep,您说don't waste anything for this thread until time expires

答案 1 :(得分:0)

我不是这方面的专家,但据我所知,多个线程一个接一个地在同一个核心上运行,所以这是CPU时间共享的问题。然后将sleep添加到无限循环将为您的导入线程提供更多资源。 要并行运行,请使用多处理。那么你的代码将使用多个核心。 你可以查看这个简单的example