java互斥锁 全局变量_线程锁(互斥锁Mutex)及递归锁

一、线程锁(互斥锁)
在一个程序内,主进程可以启动很多个线程,这些线程都可以访问主进程的内存空间,在Python中虽然有了GIL,同一时间只有一个线程在运行,可是这些线程的调度都归系统,操作系统有自身的调度规则,所以就可能造成,

假设两个线程都在访问 global count= 0, 每个进程都会执行 count +=1 。(1)(2)(3)第一个线程申请GIL然后,读取global count到及进程到 cpu ,(4)然后cpu执行到一半,(5)把这个线程停了,将上下文保存到自身寄存器中。注意这时候没返回结果。这时候解释器就会把GIL释放,

(6)(7)(8)第二个线程申请GIL执行如上步骤,读取count= 0 ,cpu计算结束后将结果count=1 返回,(10)(11)解释器拿到结果进行赋值,此时count=1,这个进程运行结束,(12)(13)然后cpu从寄存器中第一个线程的执行状态,继续执行,注意这个读取的是寄存器中的上下文,就是第一次执行时 count= 0,及第一个线程的上下文。计算结果返回count =1 返回。就造成了结果的错误。

987371df53ba0859f1768f188ae96f21.png

1.1 python中的线程锁(互斥锁mutex)
使用threading模块中的Lock类,得到一个全局锁实例。然后 Lock()实例下 有一个 acquire 方法为加锁, release 方法释放锁

import threading

count = 0

lock = threading.Lock() #申请一个锁

def count_():

global count #声明为全局变量

lock.acquire() #加锁,锁释放前不予许其他程序执行

count += 1

lock.release() #执行完 ,释放锁

thread_list = []

for i in range(10):

t = threading.Thread(target= count_)

t.start()

thread_list.append(t)

for t in thread_list:

t.join() #主程序等待所有程序执行完毕

print('Count:{: ^4}'.format(count))

1.2 递归锁
基本用不上,主要目的就是防止锁里面加锁,然后程序无法解锁退出。

import threading,time

def run1():

print("grab the first part data")

lock.acquire()

global num

num +=1

lock.release()

return num

def run2():

print("grab the second part data")

lock.acquire()

global num2

num2+=1

lock.release()

return num2

def run3():

lock.acquire()

res = run1()

print('--------between run1 and run2-----')

res2 = run2()

lock.release()

print(res,res2)

if __name__ == '__main__':

num,num2 = 0,0

lock = threading.RLock()

for i in range(10):

t = threading.Thread(target=run3)

t.start()

while threading.active_count() != 1:

print(threading.active_count())

else:

print('----all threads done---')

print(num,num2)

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值