保存和加载以列表作为值的熊猫数据帧不一致



我有一个熊猫数据帧,其中一列包含列表作为值。 例如:

a = [(1,1,[1,2]),(2,2,[2,3,4])]
In [75]: pd.DataFrame.from_records(a,columns=['a','b','c'],exclude='b')
Out[75]:
   a          c
0  1     [1, 2]
1  2  [2, 3, 4]

如您所见,c列实际上包含一个列表。 这是由以下人员验证的:

In [76]: _.c.ix[0]
Out[76]: [1, 2]

因此,在这里,数据帧包含真正的列表,可用于以后使用所有列表类功能进行分析。但是当我保存数据帧然后再次加载它时,列表变为字符串:

In [72]: _.to_csv(r'D:test.csv')
In [73]: pd.read_csv(r'D:test.csv')
Out[73]:
   Unnamed: 0  a          c
0           0  1     [1, 2]
1           1  2  [2, 3, 4]
In [74]: _.c.ix[0]
Out[74]: '[1, 2]'

而且我失去了列表功能。这是一个错误吗?

不,这不是错误。CSV 文件没有数据类型信息。加载文件时,read_csv要做的就是文本。当它在文件中看到[1, 2]时,它不会假定它应该将内容作为列表进行处理。(这是正确的;CSV 文件可能包含该格式的文本,这些文本不应是列表。

直接回答:如果要将列转回列表,请df['c'] = df['c'].map(ast.literal_eval)。(当然,您必须先import ast。您可以将其写入"转换器"函数以在加载时执行此操作 - 请参阅read_csv文档。

更好的方法:将数据另存为 CSV 以外的内容,以便在加载时可以保存和恢复数据类型。最简单的方法是另存为二进制文件:df.to_pickle('test.df')

大局:包含列表的数据帧或系列是不合时宜的:它们不是很方便处理,而且它们不能提供熊猫处理数据的大部分好工具。再想想你是否真的需要你的数据作为列表。(也许你会这样做,但这应该是最后的手段。

最新更新