如果/我应该使用线程更新全局变量怎么办.[pythonic方式] [英] What if/ should I use threading to update global variables.[pythonic way]

查看:35
本文介绍了如果/我应该使用线程更新全局变量怎么办.[pythonic方式]的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个更新全局/类变量的函数.那么,定期调用子线程等函数后应该注意什么?(异步方式)

I have a function to update a global/class variable. So, What should care after regularly invoke such function as subthread?(in asynchronous way)

或者,有什么建议可以避免使用这种模式?(病态的方式)

Or, any suggestions to avoid using this pattern? (the pathonic way)

import time
import threading

# through global variable or class variable
_a = 123


def update_a():        # may be called more than once
    "slow updating process"
    time.sleep(3)
    global _a
    _a += 10
    return

if __name__ == '__main__':
    print(_a)
    th = threading.Thread(target=update_a)
    th.setDaemon(True)
    th.start()
    print(_a)
    # updating aynchrounously
    time.sleep(5)
    print(_a)

推荐答案

这表明 添加不是线程安全的(请参阅 Josiah Carlson 的评论.effbot.org 现在似乎已关闭;您可以查看存档版本通过 这里的回程机.):

This demonstrates that addition is not threadsafe (See Josiah Carlson' comment. effbot.org seems to be down right now; you can check out an archived version of the page through the wayback machine here.):

import threading
x = 0
def foo():
    global x
    for i in xrange(1000000):
        x += 1
threads = [threading.Thread(target=foo), threading.Thread(target=foo)]
for t in threads:
    t.daemon = True
    t.start()
for t in threads:
    t.join()
print(x)

产生一些小于 2000000 的数字.这表明对 x += 1 的一些调用没有正确更新变量.

yields some number less than 2000000. This shows that some calls to x += 1 did not properly update the variable.

解决方案是使用锁保护对全局变量的赋值:

The solution is to protect assignment to your global variable with a lock:

lock = threading.Lock()
def safe_foo():
    global x
    for i in xrange(1000000):
        with lock:
            x += 1

x = 0
threads = [threading.Thread(target=safe_foo), threading.Thread(target=safe_foo)]
for t in threads:
    t.daemon = True
    t.start()
for t in threads:
    t.join()
print(x)

产量为 2000000.

yields 2000000.

这篇关于如果/我应该使用线程更新全局变量怎么办.[pythonic方式]的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆