前面说到了python多线程是为了让一个程序同时干两件或者多件事情,达到多任务功能。那么问题又来了,同时干多件事情的时候,多件事情之间会不会有影响呢?比如A线程要修改num=1这个变量,B线程也要修改num=1这个变量,那么这个时候到底听谁的?再举个取钱的例子(貌似别人讲线程的时候也喜欢用取钱这个例子),假如小明的银行卡里有10000元,他在ATM机上取出1000元(A线程)的同时也通过从银行卡转出1000元到支付宝(B线程)。假如A线程取出了1000块钱,ATM机系统还没来得及将余额减去1000元,此时卡上余额依然是10000元。与此同时B线程开始转出到支付宝余额减去1000变成了9000元,然后A线程执行完成余额减去1000,变成了9000元。于是小明合计取出了2000元,余额还剩9000元,是不是很赞呢?银行可不做这种亏本生意。。。将AB两个线程加锁,当A线程加锁的时候,B线程都处于block(阻塞)的状态,等到A线程执行完之后再释放锁。此时轮到B线程加锁,执行,释放锁。这样就能保证两个线程之间互不影响。

先来一个没有锁机制的情况,取钱,存钱动作

#coding=utf-8
import threading
import time
money=10000
#通过线程的RLock()方法得到线程锁
mylock=threading.RLock()
def save_money(save):
    #mylock.acquire()#获得线程锁资源,此时其他线程都会变为block状态,停止运行
    global money
    money=money+save
    time.sleep(1)
    #mylock.release()#线程的逻辑执行完成之后释放线程锁资源,此时其他线程可以调用acquire()方法获得线程锁,独占CPU资源
    print "after saving money,the total money is %d"%(money)
def take_money(take):
    #mylock.acquire()
    global money
    money=money-take
    time.sleep(1)
    #mylock.release()
    print "after taking money,the total money is %d"%(money)
t1=threading.Thread(target=save_money,args=(1000,))#线程的另一种创建对象的方法,没有run函数了
t2=threading.Thread(target=save_money,args=(1000,))
t3=threading.Thread(target=take_money,args=(100,))
t4=threading.Thread(target=take_money,args=(100,))
t1.start()
t2.start()
t3.start()
t4.start()
t1.join()
t2.join()
t3.join()
t4.join()

  以下是执行结果,从结果中可以看出不管是存钱还是取钱,最后的结果都是11800.乱套了,达不到我们的要求

python锁 python锁机制_线程锁

去掉锁机制的注释之后,可以看到如下运行结果,每一步都很有条理。两次存钱结果分别是11000和12000,两次取钱,结果分别是11900和11800.

python锁 python锁机制_线程锁_02

请注意,在线程mylock.acquire()得到线程锁而且线程中的逻辑执行完之后,一定要记得mylock.release()释放线程锁,不然会导致其他线程得不到锁而造成死锁。