Python 的 gil 到底解决了什么具体的问题?

发布于 2021-05-20 22:55:41

如题,用了这么多年 py,Gil 按理说应该很熟悉了,但是今天被问到 Gil 具体锁了哪些东西的时候却被问住了。毕竟虽然引入了 gil 机制,但 py 中的线程争用资源由于原子性问题仍然需要用户自行上锁,细究的话很多文章讲的加入 Gil 后避免细粒度锁其实是不对的,因为用户层面并没有实现无锁感知。

具体来说,例如放两个线程同时在各自负责的内存空间操作完全不相干的对象时(比如双线程同时计算质数,各自维护各自的资源),那么按照大多数语言的思路,由于没有资源争用,实际上并不需要加锁(反之,如果有争用则必须加锁,目前 py 中也是这么干的),如果这么考量的话,Gil 所谓的有锁线程才允许解释,又解决了什么问题呢,完全没必要不是么

查看更多

关注者
0
被浏览
501
3 个回答
ipwx
ipwx 2021-05-20
这家伙很懒,什么也没写!
  1. Python 解释器层面的一些锁。这个其实想要优化总能优化的。
  2. 保护 C 扩展模块,这方面是挺蛋疼的。

Python 生态半壁江山是 C 扩展库撑起来的,丢掉这部分江山等于自废武功。为了支持无锁而去掉 GIL 等于丢掉所有这些库,做网络应用的是爽了,但是 Python 就分裂了。

说的更明确一些:哪怕 C 扩展库对自己的逻辑进行了加锁,但是由于要访问 Python 对象,进一步使用 Python 解释器的东西,它防止不了外面的代码同时访问相同的对象,然后就崩溃了。。。

所以面对 C 扩展库,GIL 喊了这么长时间都搞不掉。
…… 所以其实 Python 成也“胶水”败也“胶水”。C 扩展库能这么容易访问 Python 底层的东西是个优势,可以迅速做一些系统层面的 API 调用、融合 C/C++ 做科学计算( PyTorch,NumPy,或者 GPU 计算),或者在暴露 C/C++ 写的核心算法为 HTTP API 。但是同样的,这个优势也让 Python 在普通的多线程网络服务器上寸步难行。

我的看法是,Python 干好科学计算这方面的事情就行了。还有就是干好工具型胶水语言该做的事情,在性能无关的领域放光(比如运维)。科学计算本来就计算密集型,本来就要独占核心一直跑,根本不会有线程上下文切换。网络服务交给专业的,比如 Go,Java,C++ 什么的。多好。。。

sagaxu
sagaxu 2021-05-20
这家伙很懒,什么也没写!

python 出道的时候(90 年代初),民用 CPU 都是单核单 CPU,十几年后才有了双核 CPU 。因为没有并行,自然而然的选择了引用计数加 GIL,实现简单又不会太影响性能。后来积攒了大量的 C 扩展,保留兼容性的同时去掉 gil 是极其困难的事情,况且必要性不高,性能不够拿扩展来凑就是了

neoblackcap
neoblackcap 2021-05-20
这家伙很懒,什么也没写!

GIL 的问题是由于当时采用引用计数这样的垃圾回收技术引出的。毕竟要保护好引用数正确,要不就是处处是小锁。要不就是一个大锁(GIL)。当时为了单线程的性能,就用了一个大锁( GIL )。
后面技术发展,大家发现其实 tracing-base 的垃圾回收方案速度也不慢,同时各种优点。于是现代化的 VM 都是 tracing gc 了。
要去掉 GIL,那是得大改啊。

撰写答案

请登录后再发布答案,点击登录

发布
问题

分享
好友

手机
浏览

扫码手机浏览