Python 使用json.dumps()的MemoryError

Python 使用json.dumps()的MemoryError,python,mysql,json,sqlalchemy,out-of-memory,Python,Mysql,Json,Sqlalchemy,Out Of Memory,我想知道将大型数组编码为json格式时,json.dump()或json.dumps()中的哪一个最有效 你能给我举一个使用json.dump()的例子吗 实际上,我正在制作一个Python CGI,它使用ORM SQlAlchemy从MySQL数据库获取大量数据,在一些用户触发的处理之后,我将最终输出存储在一个数组中,最后转换为Json 但在转换为JSON时: print json.dumps({'success': True, 'data': data}) #data is my arra

我想知道将大型数组编码为json格式时,
json.dump()
json.dumps()
中的哪一个最有效

你能给我举一个使用
json.dump()
的例子吗

实际上,我正在制作一个Python CGI,它使用ORM SQlAlchemy从MySQL数据库获取大量数据,在一些用户触发的处理之后,我将最终输出存储在一个数组中,最后转换为Json

但在转换为JSON时:

 print json.dumps({'success': True, 'data': data}) #data is my array
我得到以下错误:

Traceback (most recent call last):
  File "C:/script/cgi/translate_parameters.py", line 617, in     <module>
f.write(json.dumps(mytab,default=dthandler,indent=4))
  File "C:\Python27\lib\json\__init__.py", line 250, in dumps
    sort_keys=sort_keys, **kw).encode(obj)
  File "C:\Python27\lib\json\encoder.py", line 209, in encode
    chunks = list(chunks)
MemoryError
因此,我猜测是使用
json.dump()
按块转换数据。有什么办法吗

除了使用
json.dump()

之外,您还可以简单地替换

f.write(json.dumps(mytab,default=dthandler,indent=4))


这将把数据“流”到文件中。

在写入之前,
JSON
模块将在内存中分配整个JSON字符串,这就是发生
MemoryError
的原因。

要解决此问题,请使用:

打开(文件路径,'w')作为f:
对于json.JSONEncoder().iterCode(object_to_encode)中的块:
f、 写入(块)
但是请注意,这通常需要相当长的时间,因为它是以许多小块的形式编写的,而不是一次完成所有内容


特殊情况:

我有一个Python对象,它是一个dict列表。例如:

[
{“prop”:1,“attr”:2},
{“prop”:3,“attr”:4}
# ...
]
我可以
JSON.dumps()
单个对象,但是转储整个列表会生成一个
MemoryError
为了加快写入速度,我打开文件并手动写入JSON分隔符:

打开(文件路径,'w')作为f:
f、 写入(“[”)
对于目录列表中的obj[:-1]:
json.dump(obj,f)
f、 写入(',')
dump(dicts[-1],f的列表)
f、 写入(']')

如果您事先知道JSON对象结构,那么您很可能会得到类似的结果。对于一般用途,只需使用
JSON.Encoder().iterencode()

我不知道实现细节,但
将输出转储到字符串,该字符串必须建立并保存在内存中<代码>转储
写入一个文件,我假设该文件是流式的,不会将结果保存在内存中。
s由
JSON.Encoder().iterencode()生成器生成。查看我的答案。即使假设示例中的
mytab
是一个JSON可序列化对象,
JSON.dump()
也不知道要转储哪个对象,这也行不通。此外,即使尝试这样做,仍然会为大型对象生成
MemoryError
。对。。忘记将mytab作为参数。固定的。关于内存,可能值得尝试其他json库,希望实现更高效的内存…最终找到了一个解决方法,发布了我的答案
:]
,这正是
json.dump
的作用:是的,但是iterencode()如果尝试大型对象,速度太慢-最好将块划分到内存可以处理的位置,然后立即将其传递给encode()。
json.dump(mytab, f, default=dthandler, indent=4)