Python全局变量是线程安全的吗?
编辑:我在问全局变量在像tornado这样的单线程web框架中是否安全 im使用mongoengine orm,该orm从全局变量获取数据库连接:Python全局变量是线程安全的吗?,python,mongodb,tornado,Python,Mongodb,Tornado,编辑:我在问全局变量在像tornado这样的单线程web框架中是否安全 im使用mongoengine orm,该orm从全局变量获取数据库连接: _get_db() # gets the db connection 我也在使用tornado,一个单线程python web框架。在一个特定视图中,我需要获取一个数据库连接并取消引用一个DBRef对象[类似于外键]: # dereference a DBRef _get_db().dereference(some_db_ref) 由于\u ge
_get_db() # gets the db connection
我也在使用tornado,一个单线程python web框架。在一个特定视图中,我需要获取一个数据库连接并取消引用一个DBRef
对象[类似于外键]:
# dereference a DBRef
_get_db().dereference(some_db_ref)
由于
\u get\u db
返回的连接是一个全局变量,因此是否存在冲突的可能性以及错误的值返回到错误的线程?在与Python对象交互时,线程总是需要持有GIL。保存变量的名称空间是Python对象(frameobject或dict,具体取决于变量的类型)。在多个线程中获取或设置变量总是安全的。你永远不会得到垃圾数据
然而,通常的竞争条件确实适用于您获得的对象,或者在分配时替换的对象。像
x+=1
这样的语句不是线程安全的,因为不同的线程可以在get和存储之间运行,从而更改x
的值,然后您将覆盖该值。全局变量并没有比任何其他变量更能保证线程安全。无论操作在不同线程中运行时是否可能失败或返回不正确的结果,最好的做法是保护线程之间共享的数据
如果我没看错的话,你是在问变量在单线程环境中是否安全。在这种情况下,在并发进程之间不共享数据的情况下,变量是安全的(毕竟,没有其他运行方式会中断它)。假设MongoEngine正在包装PyMongo(我相信是的),那么您应该可以。PyMongo是完全线程安全的。不,但是在python中使用锁非常简单。使用try:finally:pattern确保在修改全局变量后释放锁。似乎这与特定库的关系大于与全局变量的关系。mongodb是否指定了get\uDB是否是线程安全的?你是说任何
x+=1
的函数或类方法都不是线程安全的?他是这么说的在线程化python中设置全局变量可能会失败-另一个线程可以在设置完变量后将其设置为不同的值。如果依赖于在代码块期间设置的值,则应使用锁。它是线程安全的,因为不会出现seg错误,但不会出现意外值。在列表和dict上循环是一个典型的例子,您可能会遇到麻烦-例如dict键可能会意外消失。是的,它包装pymongo,但将pymongo.Connection实例存储在全局变量中。这很好-共享连接实例是安全的。