Python 3.x pickle.dumps中的较小字符串

Python 3.x pickle.dumps中的较小字符串,python-3.x,compression,pickle,Python 3.x,Compression,Pickle,我在想办法把泡菜串变小。pickle字符串将驻留在脚本中,不能是文件 下面的例子是一本小词典,我不知道它的内容。注意字符串中有多少是\x。我试图压缩的字符串长度为93878个字符。我的一个限制是它需要使用普通的python库。我尝试过使用gzip,然后从中获取字符串。它可以保存大约2k个字符。多存点钱就好了 任何关于使用pickle或类似的香草python包来减小字符串大小的建议都是非常好的。 (在本例中,字符数少于pickle string,但通常情况并非如此。) 将字符计数从93878减少到

我在想办法把泡菜串变小。pickle字符串将驻留在脚本中,不能是文件

下面的例子是一本小词典,我不知道它的内容。注意字符串中有多少是\x。我试图压缩的字符串长度为93878个字符。我的一个限制是它需要使用普通的python库。我尝试过使用gzip,然后从中获取字符串。它可以保存大约2k个字符。多存点钱就好了

任何关于使用pickle或类似的香草python包来减小字符串大小的建议都是非常好的。 (在本例中,字符数少于pickle string,但通常情况并非如此。)


将字符计数从93878减少到72688。

一个廉价的解决方案是放弃一些pickle数据并使用Numpy的
tobytes
功能。在我的机器上:

>>> y = {k: v.tobytes() for k, v in x.items()}
>>> len(pickle.dumps(x))
298
>>> len(pickle.dumps(y))
114
当然,代价是您没有在此处保留
dtype
,但是在pickle中保存
“int”
仍然便宜得多,特别是如果所有数组的类型都相同的话

然后,您可以使用
zlib做得更好:

>>> import zlib
>>> len(zlib.compress(pickle.dumps(y))
59

压缩
x
只会降低到207,所以就没有那么理想了。

这是因为
\x
表示十六进制代码的开始,并描述了每个代码应该在哪里。我认为把pickle输出作为字符串来处理是个坏主意。你为什么要泡菜?为什么不直接转储原始数据(如果你真的需要,可以压缩它)?我试了一下。但是它只保存了1k个字符。93878对92869。使用zlib,我可以将字符串中的字符减少到92572个。字典中的数字是浮点数。@WalterGordy首先,请参阅我对使用
zlib
的编辑。其次,您的示例显然与实际数据太不一样了——在您的示例中,Python/Numpy结构是不可忽略的。在您的数组中,它们似乎是(即许多数字)。此外,您可以为每个数字使用位表示,特别是考虑到这些是浮点数,这可能意味着您无法压缩太多。我相信在
zlib
之后,你不会发现更多的东西需要压缩。我喜欢你的想法,并添加了更多的字符删除。我用一个代码示例编辑了我的问题。@WalterGordy这不是一个讨论论坛。你喜欢回答问题/答案,接受你认为已经解决了问题的答案等等。你可以在回答下面的评论中寻求帮助,但是编辑一个问题后答案被认为是非常糟糕的形式。请考虑回复你的编辑。@瓦尔特哥尔迪关于你的实际问题-任何更多的压缩将不得不以数据损失为代价-截断你的浮动,合并类似的值等。而且相当复杂。我可以在我的答案中添加一些,但我不确定这是否值得你的努力,这取决于你的需要。
>>> y = {k: v.tobytes() for k, v in x.items()}
>>> len(pickle.dumps(x))
298
>>> len(pickle.dumps(y))
114
>>> import zlib
>>> len(zlib.compress(pickle.dumps(y))
59