zoukankan      html  css  js  c++  java
  • day36

    今日内容

      1.GIL解释器锁

      2.GIL解释器锁与自定义锁

      3.死锁现象与递归锁

      4.信息量

      5.Event

      6.线程queue

    1.GIL解释器锁

    from multiprocessing import Process
    '''
    因为Cpython解释器中有一个垃圾回收机制,而每个进程下的线程运行代码时,都需要调用该进程内的Cpython解释器代码,同时每一段进程内都会有一个垃圾回收线程,
    若Cpython解释器没有这一个GIL锁就会导致线程在运行代码的同时,垃圾回收线程也被同时运行,就会有可能将普通线程产生的一些空间直接当作垃圾被垃圾回收线程
    回收,这样就是一种thread safe,所以GIL解释器锁的作用就是为了保证thread safe。
    '''
    from threading import Thread
    import time,os
    
    def task():
        time.sleep(2)
        # n=0
        # for i in range(10000000):
        #     n+=i
    
    
    if __name__ == '__main__':
        print(os.cpu_count())
        l=[]
        for i in range(8):
            s = time.time()
            # p = Process(target=task)
            t = Thread(target=task)
            l.append(t)
            t.start()
        for i in l:
            i.join()
        print(time.time()-s)
    

      

    2.GIL解释器锁与自定义锁

    自定义锁时用来将python代码中的一部分代码从并发变成串行的

    from threading import  Thread,Lock
    import time
    metux = Lock()
    n = 100
    def task():
        global n
        metux.acquire()
        temp = n
        time.sleep(0.1)
        n=temp-1
        metux.release()
    
    if __name__ == '__main__':
        l = []
        for i in range(100):
            p = Thread(target=task)
            l.append(p)
            p.start()
    
        for i in l:
            i.join()
        print(n)
    

      

    3.死锁现象与递归锁

    死锁现象

    正常的互斥锁,如果被多次使用,是很容易出现死锁现象的,所以应该使用递归锁

    from threading import Thread,Lock
    import time
    
    
    class Mythread(Thread):
        def run(self):
            foo1(self.name)
            foo2(self.name)
    metuxA = Lock()
    metuxB = Lock()
    def foo1(name):
        metuxA.acquire()
        print('%s抢到了A锁'%name)
        metuxB.acquire()
        print('%s抢到了B锁' % name)
        metuxB.release()
        metuxA.release()
    
    def foo2(name):
        metuxB.acquire()
        print('%s抢到了B锁' % name)
        time.sleep(2)
        metuxA.acquire()
        print('%s抢到了A锁' % name)
        metuxB.release()
        metuxA.release()
    
    if __name__ == '__main__':
        for i in range(10):
            p = Mythread()
            p.start()
    

      

    递归锁RLock

    递归锁:实在锁上加一个标签如果上一次锁就加一,解锁就减一,直到标签为0才能被别的线程再去使用,否则别的线程一直处于阻塞状态

    from threading import Thread,RLock
    import time
    
    
    class Mythread(Thread):
        def run(self):
            foo1(self.name)
            foo2(self.name)
    metuxA = RLock()
    metuxB = RLock()
    def foo1(name):
        metuxA.acquire()
        print('%s抢到了A锁'%name)
        metuxB.acquire()
        print('%s抢到了B锁' % name)
        metuxB.release()
        metuxA.release()
    
    def foo2(name):
        metuxB.acquire()
        print('%s抢到了B锁' % name)
        time.sleep(2)
        metuxA.acquire()
        print('%s抢到了A锁' % name)
        metuxB.release()
        metuxA.release()
    
    if __name__ == '__main__':
        for i in range(10):
            p = Mythread()
            p.start()
    

      

    4.信息量

    from threading import Thread,Semaphore
    import time,random
    xh = Semaphore(5)
    
    def task(name):
        xh.acquire()
        print('%s进入图书馆'%name)
        time.sleep(random.randint(1,3))
        # print('%s离开图书馆' % name)
        xh.release()
    
    if __name__ == '__main__':
        for i in range(20):
            q = Thread(target=task,args=('路人%s'%i,))
            q.start()
    

      

    5.Event

    from threading import Thread,Event
    import time
    event = Event()
    def light():
        print('红灯亮起,无法通行')
        time.sleep(3)
        event.set()
        print('绿灯亮起,车辆通行')
    
    def task(name):
        print('车辆%s,正在等待'%name)
        event.wait()
        print('车辆%s,通过'%name)
    
    if __name__ == '__main__':
        t1 = Thread(target=light)
        t1.start()
    
        for i in range(10):
            t = Thread(target=task,args=(i,))
            t.start()
    

      

    6.线程queue

    import queue
    
    # q = queue.Queue()#队列 先进先出
    # q.put('阿飞')
    # q.put('大猴子')
    # q.put('天天笑')
    #
    # print(q.get())
    # print(q.get())
    # print(q.get())
    # q = queue.LifoQueue()#堆栈 先进后出
    # q.put('阿飞')
    # q.put('大猴子')
    # q.put('天天笑')
    #
    # print(q.get())
    # print(q.get())
    # print(q.get())
    q = queue.PriorityQueue()#优先级 优先级越高先出(数字越小优先级越高)
    q.put((1,'阿飞'))
    q.put((5,'大猴子'))
    q.put((-6,'天天笑'))
    
    print(q.get())
    print(q.get())
    print(q.get())
    

      

  • 相关阅读:
    URAL 2046 A
    URAL 2056 Scholarship 水题
    Codeforces Gym 100286I iSharp 水题
    Codeforces Gym H. Hell on the Markets 贪心
    Codeforces Gym 100286G Giant Screen 水题
    Codeforces Gym 100286B Blind Walk DFS
    Codeforces Gym 100286F Problem F. Fibonacci System 数位DP
    Codeforces Gym 100286A. Aerodynamics 计算几何 求二维凸包面积
    Codeforces Gym 100418K Cards 暴力打表
    Codeforces Gym 100418J Lucky tickets 数位DP
  • 原文地址:https://www.cnblogs.com/yaoxiaofeng/p/9606684.html
Copyright © 2011-2022 走看看