Python中什么时候可以干掉GIL?CPU和IO密集场景下多线程如何利用多核
null
Python中什么时候可以干掉GIL?CPU和IO密集场景下多线程如何利用多核
开个 30 的线程池,开销估计都抵不上一个进程
GIL(全局解释器锁)是CPython解释器的历史遗留问题,它确实限制了多线程在CPU密集型任务中的并行能力。不过,在特定场景下,我们可以绕过GIL的限制:
CPU密集型场景: 直接用多线程跑CPU任务确实会被GIL卡住,这时候得换思路:
- 用
multiprocessing模块创建多个进程,每个进程有自己的Python解释器和内存空间,完全避开GIL - 或者用
concurrent.futures.ProcessPoolExecutor,用起来更简单
from multiprocessing import Pool
import math
def compute(n):
return sum(math.sqrt(i) for i in range(n))
if __name__ == '__main__':
with Pool(processes=4) as pool:
results = pool.map(compute, [1000000] * 8)
print(f"Results: {results}")
IO密集型场景: 这种时候多线程其实挺好用的,因为线程在等待IO(网络请求、文件读写)时会释放GIL:
- 标准库的
threading模块就够用了 - 或者用
concurrent.futures.ThreadPoolExecutor,写起来更简洁 - 现在更推荐用
asyncio做异步IO,性能更好
import concurrent.futures
import requests
def fetch_url(url):
resp = requests.get(url)
return len(resp.content)
urls = ['http://example.com'] * 10
with concurrent.futures.ThreadPoolExecutor(max_workers=5) as executor:
results = list(executor.map(fetch_url, urls))
print(f"Fetched {len(results)} pages")
关于干掉GIL: Python核心团队确实在推进无GIL的CPython(PEP 703),3.13已经提供了实验性的无GIL构建选项。但这玩意要默认开启还得等几年,主要是兼容性问题太头疼。现阶段生产环境还是用多进程处理CPU任务更靠谱。
简单说:CPU用多进程,IO用多线程或异步。
有 CPU 密集建议写到 c 里或者换语言
python 太慢不适合
gogogo
多进程走起
多进程啊
要不就换语言呗
www.python.org/dev/peps/pep-0554 参考下这个 PEP 的进度,3.9 会支持多 runtime 的基础模式,按照这个进度,应该是 2-3 个版本可以实现一个进程内的多 runtime 并行执行,也就达到充分利用多核的目的了
www.youtube.com/watch?v=7RlqbHCCVyc
有些 pandas 做的数据分析的脚本,但是里面读库,在 pandas 操作,我如果开多进程的话,占内存,应为 python 多进程不能共享 DataFrame 对象,Manager 不支持 pandas 对象,所以进程不能多开,如果没有 GIL 的话,我开 30 的线程池,不占内存,有快
为啥非得用一种语言解决

