zoukankan      html  css  js  c++  java
  • python-- 锁Lock

    银行存取钱

    银行存取钱是同时对一个数据操作,容易造成数据混乱,解决方法是加锁

    from multiprocessing import Process
    from time import sleep
    
    
    def get_money(num):  # 取钱
        num -= 1
        print('子进程:', num)
    
    
    if __name__ == '__main__':
        money_num = 100
        p = Process(target=get_money, args=(money_num,))
        p.start()
        p.join()  # 等子进程结束
        print(money_num)

    结果:

    子进程: 99
    100

    数据不共享原因导致的

    共享内存

    from multiprocessing import Process, Value
    from time import sleep
    
    
    def get_money(num):  # 取钱
        num.value -= 1
        print('子进程:', num.value)
    
    
    if __name__ == '__main__':
        money_num = Value('i', 100)
        p = Process(target=get_money, args=(money_num,))
        p.start()
        p.join()
        print(money_num.value)

    结果:

    子进程: 99
    99

    要共享内存有多个方法,这里用Value,首先要导入,money_num=Value('i',100)这句话的Value接收两个参数,第一个是数据类型,第二个是这个类型的值,取值的时候要用x.value

    银行取钱问题

    from multiprocessing import Process, Value
    from time import sleep
    
    
    def get_money(num):  # 取钱
        for i in range(100):
            num.value -= 1
            sleep(0.01)
    
    
    def put_money(num):  # 存取
        for i in range(100):
            num.value += 1
            sleep(0.01)
    
    
    if __name__ == '__main__':
        money_num = Value('i', 100)
        p = Process(target=get_money, args=(money_num,))
        p.start()  # 取钱
        p1 = Process(target=put_money, args=(money_num,))
        p1.start()  # 存取
        p1.join()
        p.join()
        print(money_num.value)

    多执行几次,有时候是100,有时候小于100,有时候大于100

    锁 Lock

    from multiprocessing import Process, Lock
    
    l = Lock()  # 实例化
    l.acquire()  # 加锁。拿走钥匙,锁门,不让其他人进屋
    l.release()  # 释放锁。还钥匙,开门,允许其他人进屋

    银行存取钱加锁

    from multiprocessing import Process, Value, Lock
    from time import sleep
    
    
    def get_money(num, l):  # 取钱
        l.acquire()
        for i in range(100):
            num.value -= 1
            sleep(0.01)
        l.release()
    
    
    def put_money(num, l):  # 存取
        for i in range(100):
            l.acquire()  # 建议小范围的加锁
            num.value += 1
            l.release()
            sleep(0.01)
    
    
    if __name__ == '__main__':
        l = Lock()  # 实例化锁
        money_num = Value('i', 100)
        p = Process(target=get_money, args=(money_num, l))
        p.start()  # 取钱
        p1 = Process(target=put_money, args=(money_num, l))
        p1.start()  # 存取
        p1.join()
        p.join()
        print(money_num.value)

    不管操作多少次都是100

    遇见l.acquire()给数据加个锁,别的进程就不能操作这个数据了,直到l.release()之后其他的进程才可以操作锁,建议小范围内加锁

    模拟 12306 强票

    from multiprocessing import Process, Lock
    import time
    
    
    def check(i):
        with open('余票') as f:
            con = f.read()
        print('第%s个人查到余票还剩%s张' % (i, con))
    
    
    def buy_ticket(i, l):
        l.acquire()  # 拿钥匙,锁门
        with open('余票') as f:
            con = int(f.read())
            time.sleep(0.1)
        if con > 0:
            print('33[31m 第%s个人买到票了33[0m' % i)
            con -= 1
        else:
            print('33[32m 第%s个人没有买到票33[0m' % i)
        time.sleep(0.1)  # 是指 买完票后,把余票数量重写写入数据库的时间延迟
        with open('余票', 'w') as f:
            f.write(str(con))
        l.release()  # 还钥匙,开门
    
    
    if __name__ == '__main__':
        l = Lock()
        for i in range(10):
            p_ch = Process(target=check, args=(i + 1,))
            p_ch.start()
        for i in range(10):
            p_buy = Process(target=buy_ticket, args=(i + 1, l))
            p_buy.start()

    新建一个 “余票” 的文件,写个12

    执行结果

    第1个人查到余票还剩12张
    第2个人查到余票还剩12张
    第3个人查到余票还剩12张
    第4个人查到余票还剩12张
    第5个人查到余票还剩12张
    第6个人查到余票还剩12张
    第7个人查到余票还剩12张
    第8个人查到余票还剩12张
    第9个人查到余票还剩12张
    第10个人查到余票还剩12张
     第1个人买到票了
     第2个人买到票了
     第3个人买到票了
     第4个人买到票了
     第5个人买到票了
     第6个人买到票了
     第7个人买到票了
     第8个人买到票了
     第9个人买到票了
     第10个人买到票了
  • 相关阅读:
    LeetCode偶尔一题 —— 617. 合并二叉树
    《剑指offer》 —— 链表中倒数第k个节点
    《剑指offer》 —— 青蛙跳台阶问题
    《剑指offer》—— 二维数组中的查找
    《剑指offer》—— 替换空格
    《剑指offer》—— 合并两个排序的链表
    《剑指offer》—— 礼物的最大价值
    生成Nuget 源代码包来重用你的Asp.net MVC代码
    Pro ASP.Net Core MVC 6th 第四章
    Pro ASP.NET Core MVC 6th 第三章
  • 原文地址:https://www.cnblogs.com/zouzou-busy/p/13775296.html
Copyright © 2011-2022 走看看