再谈Python的GIL(续)


《再谈Python的GIL》这篇文件中漏掉了一个很重要的函数没有讨论到:sys.setcheckinterval

该函数用于设置GIL自动切换的间隔,默认值为100,之前的测试都是在默认值下得出来的结果,接下来我们来再通过例子做个实验,将checkinterval设置成1000,看下是什么情况

3.1 测试用例:

from threading import Thread

from threading import Event as TEvent

from multiprocessing import Process

from multiprocessing import Event as PEvent

from timeit import Timer

import sys

sys.setcheckinterval(1000) #(100000)

def countdown(n,event):

    while n > 0:

        n -= 1

    event.set()

def io_op(n,event,filename):

    f = open(filename,'w')

    while not event.is_set():

        f.write('hello,world')

    f.close()

def t1():

    COUNT=100000000

    event = TEvent()

    thread1 = Thread(target=countdown,args=(COUNT,event))

    thread1.start()

    thread1.join()

def t2():

    COUNT=100000000

    event = TEvent()

    thread1 = Thread(target=countdown,args=(COUNT//2,event))

    thread2 = Thread(target=countdown,args=(COUNT//2,event))

    thread1.start(); thread2.start()

    thread1.join(); thread2.join()

def t3():

    COUNT=100000000

    event = PEvent()

    p1 = Process(target=countdown,args=(COUNT//2,event))

    p2 = Process(target=countdown,args=(COUNT//2,event))

    p1.start(); p2.start()

    p1.join(); p2.join()

def t4():

    COUNT=100000000 #00000

    event = TEvent()

    thread1 = Thread(target=countdown,args=(COUNT,event))

    thread2 = Thread(target=io_op,args=(COUNT,event,'thread.txt'))

    thread1.start(); thread2.start()

    thread1.join(); thread2.join()

def t5():

    COUNT=100000000 #00000

    event = PEvent()

    p1 = Process(target=countdown,args=(COUNT,event))

    p2 = Process(target=io_op,args=(COUNT,event,'process.txt'))

    p1.start(); p2.start()

    p1.join(); p2.join()

if __name__ == '__main__':

    t = Timer(t1)

    print('countdown in one thread:%f'%(t.timeit(1),))

    t = Timer(t2)

    print('countdown use two thread:%f'%(t.timeit(1),))

    t = Timer(t3)

    print('countdown use two Process:%f'%(t.timeit(1),))

    t = Timer(t4)

    print('countdown in one thread with io op in another thread:%f'%(t.timeit(1),))

    t = Timer(t5)

    print('countdown in one process with io op in another process:%f'%(t.timeit(1),)) 


输出:

countdown in one thread:7.867444

countdown use two thread:9.830585

countdown use two Process:2.148110

countdown in one thread with io op in another thread:7.691811

countdown in one process with io op in another process:7.477607

结论:

是的,countdown在多线程情况下的效率得到了极大的提升,原因就线程的有效运行率大大提高了,当切换到线程时,线程得以运行的机会提高了。

但是这会导致I/O的性能大大的降低。thread.txt的大小为2161KB,而process.txt的大小则为22401KB

而在checkinterval值为默认值100时则thread.txt和process.txt的大小相当。

(完)

相关内容

    暂无相关文章

评论关闭