当最近更新运行Ubuntu的计算机并且默认版本的Python更改为2.7时,我注意到了这个问题。
import json
import numpy as np
json.dumps(list(np.arange(5))) # Fails, throws a "TypeError: 0 is not JSON serializable"
json.dumps(np.arange(5).tolist()) # Works
list()和numpy数组的tolist()方法有区别吗?
答案 0 :(得分:24)
因为NumPy数组的元素不是本机int,而是NUmPy自己的类型:
>>> type(np.arange(5)[0])
<type 'numpy.int64'>
您可以使用自定义JSONEncoder
来支持ndarray
返回的arange
类型:
import numpy as np
import json
class NumPyArangeEncoder(json.JSONEncoder):
def default(self, obj):
if isinstance(obj, np.ndarray):
return obj.tolist() # or map(int, obj)
return json.JSONEncoder.default(self, obj)
print(json.dumps(np.arange(5), cls=NumPyArangeEncoder))
答案 1 :(得分:23)
看起来tolist()
方法将numpy int32
(或任何大小)变回int
,JSON知道如何处理:
>>> list(np.arange(5))
[0, 1, 2, 3, 4]
>>> type(list(np.arange(5)))
<type 'list'>
>>> type(list(np.arange(5))[0])
<type 'numpy.int32'>
>>> np.arange(5).tolist()
[0, 1, 2, 3, 4]
>>> type(np.arange(5).tolist())
<type 'list'>
>>> type(np.arange(5).tolist()[0])
<type 'int'>
正如文档所说tolist()
:
将数组作为(可能是嵌套的)列表返回。
将数组数据的副本作为(嵌套)Python列表返回。 数据项 转换为最接近的兼容Python类型。
最后一行在这里有所不同。
答案 2 :(得分:1)
问题是,第一个你没有得到一个int。你得到一个numpy.int64。这不能序列化。