python - Python重启后Gzip输出不同
问题描述
我正在尝试在 Python 3.6.8 中压缩一个 numpy 数组。
如果我运行这个片段两次(不同的解释器会话),我会得到不同的输出:
import gzip
import numpy
import base64
data = numpy.array([[1.0, 2.0, 3.0, 4.0], [5.0, 6.0, 7.0, 8.0], [9.0, 10.0, 11.0, 12.0], [13.0, 14.0, 15.0, 16.0]])
compressed = base64.standard_b64encode(gzip.compress(data.data, compresslevel=9))
print(compressed.decode('ascii'))
示例结果(每次都不一样):
H4sIAPjHiV4C/2NgAIEP9gwQ4AChOKC0AJQWgdISUFoGSitAaSUorQKl1aC0BpTWgtI6UFoPShs4AABmfqWAgAAAAA==
H4sIAPrHiV4C/2NgAIEP9gwQ4AChOKC0AJQWgdISUFoGSitAaSUorQKl1aC0BpTWgtI6UFoPShs4AABmfqWAgAAAAA==
^
在循环中运行它(所以相同的解释器会话),每次都会给出相同的结果
for _ in range(1000):
assert compressed == base64.standard_b64encode(gzip.compress(data.data, compresslevel=9))
我怎样才能每次都得到相同的结果?(最好没有外部库。)
解决方案
Gzip 在压缩时会使用一些文件信息(inode、时间戳等)(此处对此进行了很好的讨论)。您本身并没有使用文件,但您仍然在不同的时间使用它。所以这可能会产生影响(看看 Python 的 gzip 包装器实际上会提供更好的洞察力,但这超出了我的范围:)
因此,如果您有 Python 3.8+,请尝试使用mtime=0
参数gzip.compress(data.data, compresslevel=9)
,如
gzip.compress(data.data, compresslevel=9, mtime=0)
如果这不起作用(例如较旧的 Python 版本),那么您可以使用gzip.GzipFile
参数mtime
,如下所示:
buf = io.BytesIO()
with GzipFile(fileobj=buf, mode='wb', compresslevel=compresslevel, mtime=0) as f:
f.write(data)
result = buf.getvalue()
有关详细信息,文档在这里:
推荐阅读
- swift - SwiftUI 2 自定义 GraphicalDatePickerStyle()
- python - PySerial 读取问题
- maven - Gradle 管理传递依赖
- pygame - 我无法让移动模块键工作,我无法选择它们
- python - Pandas DataFrame 使用另一个 DataFrame 列过滤行
- php - Cakephp media() 不允许变量链接.. 导致 preg_match() 错误
- python - 在 python 3 中保存特定文件名的问题
- java - 为什么会出现 ArrayOutOfBounds 异常?
- javascript - 如何查询 mapbox 地图的 json 对象属性?
- assembly - 为什么 Bochs 在简单的 mov 指令上崩溃