在长时间运行的Python脚本中保持内存数据与文件同步
我有一个Python(2.7)脚本,它充当服务器,因此会长时间运行。这个脚本需要跟踪一些值,这些值会根据客户端的输入随时变化。
我希望能有一个东西,可以在内存中保存一个Python的数据结构(包含 dict
、list
、unicode
、int
和 float
类型的值,也就是类似JSON的格式),让我可以随意更新这些值(除了不能多次引用任何引用类型的实例),同时还要能把这些数据保持在一个人类可读的文件中,这样即使突然断电,服务器也能重新启动并继续使用相同的数据。
我知道我说的基本上就是在谈论数据库,但我保存的数据非常简单,通常也不会超过1 kB,所以我在寻找一个尽可能简单的解决方案,能够提供我所描述的数据完整性。有没有好的Python(2.7)库可以让我做到这一点?
5 个回答
有没有什么特别的原因需要人类可读的格式呢?
我建议你可以看看sqlite,这是一种简单的数据库解决方案;或者使用pickle,这是一种简单的方法,可以把对象保存到磁盘上。不过这两种方式都不是特别容易让人看懂。
你提到的其他选择还有JSON或者XML。你可以使用内置的json模块来把对象转成JSON格式,然后把它写入磁盘。当你启动程序时,检查一下这个文件是否存在,如果存在就加载数据。
来自文档:
>>> import json
>>> print json.dumps({'4': 5, '6': 7}, sort_keys=True, indent=4)
{
"4": 5,
"6": 7
}
好吧,既然我们基本上是在讨论一个数据库,虽然是个很简单的数据库,你可能不会感到惊讶,我建议你看看 sqlite3 这个模块。
我同意你不需要一个复杂的数据库,因为看起来你只想要简单的文件写入。你需要把这个问题分成两部分来解决:序列化/反序列化和原子写入。
在第一部分,json
或者pickle
可能是适合你的格式。JSON的好处是人类可以读懂。不过,看起来这并不是你面临的主要问题。
一旦你把对象序列化成字符串,可以使用以下方法将文件原子性地写入磁盘,假设只有一个同时写入的程序(至少在POSIX系统上,下面会提到):
import os, platform
backup_filename = "output.back.json"
filename = "output.json"
serialised_str = json.dumps(...)
with open(backup_filename, 'wb') as f:
f.write(serialised_str)
if platform.system() == 'Windows':
os.unlink(filename)
os.rename(backup_filename, filename)
虽然os.rename
可以覆盖已有的文件,并且在POSIX系统上是原子操作,但在Windows上情况就不一样了。在Windows上,os.unlink
可能会成功,但os.rename
可能会失败,这样的话你就只会有backup_filename
而没有filename
。如果你要在Windows上运行,就需要考虑这种可能性,在检查filename
是否存在时要特别注意。
如果有可能有多个同时写入的程序,你就需要考虑使用同步机制。