1 Star 0 Fork 0

趣味AI / python-small-examples

加入 Gitee
与超过 1200万 开发者一起发现、参与优秀开源项目,私有仓库也完全免费 :)
免费加入
该仓库未声明开源许可证文件(LICENSE),使用请关注具体项目描述及其代码上游依赖。
克隆/下载
122.md 1.60 KB
一键复制 编辑 原始数据 按行查看 历史
vuefine 提交于 2020-08-23 12:40 . md-head
@author jackzhenguo
@desc 
@date 2019/10/28

122 多线程变量竞争引起的问题

只要弄明白问题暴露的原因,叫问题出现还是不困难的。

想象数据库的写入操作,一般需要耗费我们可以感知的时间。

为了模拟这个写入动作,简化期间,我们只需要延长修改变量a的时间,问题很容易就会还原出来。

import threading
import time


a = 0
def add1():
    global a    
    tmp = a + 1
    time.sleep(0.2) # 延时0.2秒,模拟写入所需时间
    a = tmp
    print('%s  adds a to 1: %d'%(threading.current_thread().getName(),a))
    
threads = [threading.Thread(name='t%d'%(i,),target=add1) for i in range(10)]
[t.start() for t in threads]

重新运行代码,只需一次,问题立马完全暴露,结果如下:

t0  adds a to 1: 1
t1  adds a to 1: 1
t2  adds a to 1: 1
t3  adds a to 1: 1
t4  adds a to 1: 1
t5  adds a to 1: 1
t7  adds a to 1: 1
t6  adds a to 1: 1
t8  adds a to 1: 1
t9  adds a to 1: 1

看到,10个线程全部运行后,a的值只相当于一个线程执行的结果。

下面分析,为什么会出现上面的结果:

这是一个很有说服力的例子,因为在修改a前,有0.2秒的休眠时间,某个线程延时后,CPU立即分配计算资源给其他线程。直到分配给所有线程后,根据结果反映出,0.2秒的休眠时长还没耗尽,这样每个线程get到的a值都是0,所以才出现上面的结果。

以上最核心的三行代码:

tmp = a + 1
time.sleep(0.2) # 延时0.2秒,模拟写入所需时间
a = tmp
1
https://gitee.com/funny_ai/python-small-examples.git
git@gitee.com:funny_ai/python-small-examples.git
funny_ai
python-small-examples
python-small-examples
master

搜索帮助