Skip to main content
 首页 » 编程设计

python cPickle unpickling错误无效加载 key

2025年05月04日7lautakyan007

python 对象是字符串和数字的嵌套列表。

文件被打开以写入“w”(不是“wb”)但 cPickle 被告知使用 protocol=1(所以二进制)。

序列化和反序列化代码在 Linux 上运行良好。我无法恢复保存在 Windows 机器 (Python 2.6) 上的对象。

我(现在)明白,由于行尾的原因,该文件应该在 Windows 中明确打开为“wb”。那就是说写入的对象是一个嵌套列表并且不包含\n 所以我不确定这是否重要。

我的问题是如何恢复数据?

这是 print repr(open(fqfn, 'rb').read(15)) 的结果:

 ']q\x01(]q\x02]q\x03(U\x0fst' 

欢迎任何想法。


我尝试将 l = cPickle.load(open(fqfn, 'r')) 作为 suggested by mhawke ,但 Windows 向我发送了 EOF 错误。

如果我直接在十六进制编辑器中打开文件,我可以简单地将 '\r\n' 的实例替换为 10 和 13 然后使用二进制模式恢复?

序列化的输入是这样的:

[['start', 3454654], [1234567645, -1 , 99], [1234567900, 1 , 56], ...] 

我知道输入的顺序、每个列表的长度和一些值(例如开头的字符串和一些数字)。

所以我想我的问题是我是否可以通过编写处理二进制编码的脚本来反序列化。我不需要将它放入 python 对象中——ascii 就足够了。

请您参考如下方法:

我想您可能已经尝试通过在 Windows 机器上以文本模式 'r'(即不是 'rb')打开文件来解压文件。如果你幸运的话,下面的方法应该有效:

import cPickle 
l = cPickle.load(open(fqfn, 'r')) 

您的数据可能不包含新行,但可能包含 10 或 13 等值。请考虑以下情况:

>>> cPickle.dumps(10, protocol=1) 
'K\n.' 
>>> cPickle.dumps(256, protocol=1) 
'M\x00\x01.' 
>>> cPickle.dumps(266, protocol=1) 
'M\n\x01.' 

第一个中的 '\n' 在那里是因为 ascii 10 是换行符,二进制 pickle 模式以这种方式存储它。同样,如果您 p​​ickle 266 (256+10),您也会在输出中看到“\n”。

在 Windows 上,当写入以“文本”模式打开的文件时,Python 会自动将 '\n' 转换为 '\r\n'。在文本模式下阅读时,它还会将 '\r\n' 转换为 '\n'。因此,在 Windows 机器上以“文本”模式打开文件应该可以解决您的问题。