我有一个执行以下操作的Python应用程序:
with shelve.open(shelvefilename, flag='c')
存储对象,with shelve.open(shelvefilename, flag='r')
问题在于,有时我会遇到_gdbm.error: [Errno 11] Resource temporarily unavailable
错误:
File "/path/to/myprog.py", line 755, in mymethod
with shelve.open(shelvefilename, flag='r') as shlvfile:
File "/usr/local/lib/python3.6/shelve.py", line 243, in open
return DbfilenameShelf(filename, flag, protocol, writeback)
File "/usr/local/lib/python3.6/shelve.py", line 227, in __init__
Shelf.__init__(self, dbm.open(filename, flag), protocol, writeback)
File "/usr/local/lib/python3.6/dbm/__init__.py", line 94, in open
return mod.open(file, flag, mode)
_gdbm.error: [Errno 11] Resource temporarily unavailable
我的猜测是,发生这种情况是因为有时我已经打开了用于读取和写入操作的搁置文件,其定义为problematic。
有什么办法可以在不干扰读取操作的情况下对搁置文件进行更新?
答案 0 :(得分:1)
这更多是一个概念性问题。如果一个进程修改了文件中的数据,而另一个进程同时读取了该文件,则结果是无法预测的。
想象一下,您读取了文件的一部分,此时该部分值只写入了一半。读取将仅无法正确解析条目,并且可能无法解析所有后续条目。换句话说,它迟早会损坏。
我认为最好的方法是将“货架”集中在一个流程中或使用数据库。
答案 1 :(得分:1)
我只是在一个用于缓存汇率的小模块中搁置了这个问题。您可以使用python线程和全局threading.Lock()
对象来解决此问题。
from threading import Lock
import shelve
mutex = Lock()
mutex.acquire()
db = shelve.open(db_name)
# write to db
db.close()
mutex.release()
此代码段和想法的原始来源可以在http://georg.io/2014/06/Python-Shelve-Thread-Safety上找到
threading.Lock()对象的工作方式是阻塞其他python线程,直到释放为止。参见https://docs.python.org/2/library/threading.html#lock-objects