GIL全局解释器锁

情到浓时终转凉″ 提交于 2019-11-28 01:07:14

GIL全局解释器锁

python解释器有很多种,最常见的就是CPython解释器

GIL本质也是一把互斥锁:将并发变成串行牺牲效率保证数据的安全

用来阻止用一进程地下的多线程的同时执行(同一进程内多个线程无法实现并行但是可以实现并发)

GIL的存在是因为CPython解释器的内存管理不是线程安全的

垃圾回收机制:引用计数,标记清除,分代回收

研究python的多线程是否有用需要分情况谈论

比如我们要开四个任务,都是计算密集型的,每个需要用时10s

在单核情况下,开线程比开进程更节省资源

在多核情况下,开进程比开线程更节省资源,比如开进程需要10s,而开线程需要40s。

# 计算密集型 在多核情况下,开线程比开线程更节省时间资源
from multiprocessing import Process
from threading import Thread
import os,time
def work():
    res = 0
    for i in range(100000000):
        res *= i

if __name__ == '__main__':
    l = []
    print(os.cpu_count())
    start = time.time()
    for i in range(4):
        p = Process(target=work)  # run time is 24.919609785079956
        # p = Thread(target=work)  # run time is 53.27436089515686
        l.append(p)
        p.start()

    for p in l:
        p.join()
        stop = time.time()
    print(f"run time is {stop-start}")
# 计算IO密集型 在多核情况下,开线程要比开进程更节省时间资源
from multiprocessing import Process
from threading import Thread
import threading
import os,time
def work():
    time.sleep(2)

if __name__ == '__main__':
    l = []
    print(os.cpu_count())
    start = time.time()
    for i in range(40):
        # p = Process(target=work)  # run is 11.970486640930176
        p = Thread(target=work)  # run is 2.0098724365234375
        l.append(p)
        p.start()

    for p in l:
        p.join()
    stop = time.time()
    print(f'run is {stop-start}')

Python的多线程到底有没有用,需要看情况而定,并且肯定是有用的。

一般都是多进程+多线程配合使用。

GIL与普通的互斥锁

在多个资源抢占同一个资源时,有GIL锁的存在让同一个进程下的多个线程无法同时执行。即只有一个线程能够抢到锁,其他的要等到锁释放之后才可以抢,保证了数据的安全。

from threading import Thread

import time

n = 100

def task():
    global n
    tmp = n
    # time.sleep(1) # 0
    time.sleep(1)  # 在睡眠一秒后,只有一个线程抢到
    n = tmp - 1

t_list = []
for i in range(100):
    t = Thread(target=task)
    t.start()
    t_list.append(t)

for t in t_list:
    t.join()

print(n)  # 99
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!