转载: https://www.cnblogs.com/2bjiujiu/p/9150380.html
GIL
全局解释锁,这个锁是个粗粒度的锁,解释器层面上的锁,为了保证线程安全,同一时刻只允许一个线程执行,但是这个锁并不能保证线程安全,因为GIL会释放掉并且切换到另一个线程上,不会完全占用,一句分配策略(时间片、执行字节码行数、IO操作).GIL只能保证同一时刻同一CPU上只有一个线程执行,但不能保证线程切换的时候能把一行代码翻译成的bytecode执行完,这就会出现问题,所以说只能一定程度上地保证线程安全.GIL使得同一时刻只有一个线程在CPU上执行字节码,无法将多个线程映射到多个CPU上,也就是说根本意义上来说python是个单线程的,这个GIL只在CPython中才有,其他版本中没有.
单线程有个非常大的优势就是在处理IO密集型的任务时显得与众不同,Python中分线程和协程两种方式,(协程、线程优缺点)线程是由系统控制调用,协程是由程序员控制,也就是说在把控角度上来看协程比线程更加具有优势.其一协程比线程更加轻量,其二协程切换完全由程序员控制而不是操作系统控制,其三协程切换消耗远比线程小.
Python代码执行原理
Python代码--->解释器--->bytecode--->一行一行执行bytecode
import dis
def add(a):
a+=1
def subtract(a):
a-=1
if __name__ == '__main__':
# add函数执行过程
dis.dis(add)
print()
# subtract函数执行过程
dis. dis(subtract)
# 结果
2 0 LOAD_FAST 0 (a)
2 LOAD_CONST 1 (1)
4 INPLACE_ADD
6 STORE_FAST 0 (a)
8 LOAD_CONST 0 (None)
10 RETURN_VALUE
2 0 LOAD_FAST 0 (a)
2 LOAD_CONST 1 (1)
4 INPLACE_SUBTRACT
6 STORE_FAST 0 (a)
8 LOAD_CONST 0 (None)
10 RETURN_VALUE
# 简化一下执行过程:
def add(a):
a += 1
add
1. load a
2. load 1
3. +
4. 赋值给a a = a +1
def subtract(a):
a -= 1
subtract
1. load a
2. load 1
3. -
4. 赋值给a a = a - 1
以上过程GIL会在其中某个过程释放掉给其他线程,问题出现在4赋值阶段,多个线程切换,最终a的值处于各自线程最终结果,假如a=1,则add线程赋值a=2,然而subtract线程赋值a=0,那么问题出现了,为了解决这个问题,引入所得概念,线程同步机制,锁住问题的代码段,锁住代码块之间串行.获得锁和释放锁带来性能问题,并且可能会带来死锁问题.