【问题标题】:Is manual pickling of numpy array cross platform?numpy数组的手动酸洗是否跨平台?
【发布时间】:2017-07-29 18:27:43
【问题描述】:

我使用 python3 来腌制一个字典,其中包含文本的文本键或带有整数 dtypescipy.sparse.lil_matrix(链表)。

该文件是否跨平台(在安装了 python3、scipy 和 numpy 的机器上)?

pickled 字典是否只包含文本和 numpy 数组跨平台?

pickle 是跨平台的:Is pickle file of python cross-platform?

numpy 的.npy 文件格式是跨平台的:Is numpy.save cross platform? ...

不确定如果我手动腌制一个 numpy 数组会发生什么。我用 intel cpu 在两台不同的机器上检查了一个整数 numpy 数组,值保持不变。

手动酸洗一个 numpy 数组:

import numpy as np
import pickle
x = np.random.randint(0, 2**63 - 1, dtype=np.int32)
d = {
    'x': x,
    'blah': "blah blah blah"
}
with open('bomb.pickle', 'wb+') as f:
    pickle.dump(d, f)

【问题讨论】:

  • 它应该是跨平台的,但要解压你需要安装 scipy 的内容。
  • 我的意思是,在其他具有不同操作系统的计算机上,如果安装了 scipy,则取消选择应该可以工作。
  • 这取决于 pickle 在 numpy 数组对象上的工作方式......如果它从内存中复制二进制字节,那么即使是整数,字节序的变化也会搞砸。如果它是内存转储,请忘记不同 cpu 的浮点格式兼容性。我不知道 numpy 数组的 C 部分是如何被 pickle 保存的。字典的 Python 部分和 numpy 数组在腌制时将是跨平台的。如果手动腌制的numpy数组是跨平台的,那么使用numpy数组构建的手动腌制的scipy稀疏矩阵也将是跨平台的。
  • 你试过 hdf5 吗?例如。使用 pytables 或 h5py。这应该考虑到所有 Python 和平台差异。
  • 这些是代码的旧部分。代码的新部分已经使用 hdf5。

标签: python python-3.x numpy scipy pickle


【解决方案1】:

如果我们不必修复导入,则使用整数 dtype 手动酸洗 numpy 数组。

这是因为如果对象有reduce方法,pickle会使用它。

numpy.ndarray.__reduce__的文档https://docs.scipy.org/doc/numpy/reference/generated/numpy.ndarray.reduce.html

“numpy ndarray 如何腌制”未引用源码:How does Python 3 know how to pickle extension types, especially Numpy arrays?

在早期,使用协议 0 的 Pickling 对于浮点数、NaN、Inf 来说不可移植https://mail.python.org/pipermail/tutor/2010-May/075980.html

使用文本协议在 python 3.1 上酸洗浮动的官方文档: https://docs.python.org/3/whatsnew/3.1.html

新算法依赖于底层的某些特征 浮点实现。如果没有找到所需的功能, 旧算法将继续使用。此外,文本泡菜 协议通过使用旧的协议确保跨平台可移植性 算法。

numpy 写入文件的源代码在format.write_arraynpyio.save

(https://github.com/numpy/numpy/blob/v1.13.0/numpy/lib/format.py, https://github.com/numpy/numpy/blob/v1.13.0/numpy/lib/npyio.py#L435-L512)

标题可以保存为文本。 如果酸洗参数为真,则数据只是一个pickle.dump,这是numpy.save 的默认值。 在format.write_array,我发现:

pickle.dump(array, fp, protocol=2, **pickle_kwargs)

format.py 还说:

.npy 格式是 NumPy 中的标准二进制文件格式 在磁盘上保存一个 single 任意 NumPy 数组。格式存储 重构所需的所有形状和数据类型信息 即使在另一台具有不同架构的机器上也能正确排列。

因此,numpy 数组的手动酸洗是跨平台的(如果我们不必修复导入),因为 np.save 也使用 pickle 并且是跨平台的。

np.save 使用协议 2。pickle.DEFAULT_PROTOCOL 是两台机器上的两个 python 3 的 3。

【讨论】:

  • 希望这意味着手动酸洗 scipy 稀疏数组也可以。
  • np.save 写入具有 shape 和 dtype 等属性的块,然后是数据缓冲区的图像(可以读取为 memmap)。 Dtype 对象通过 pickle 保存。相反,数组的泡菜是它的save
  • 我不确定用于稀疏类的泡菜;它们不是np.ndarray 的子类。最近的 scipy 版本有一个 sparse.save_npz 函数,它创建一个带有所需数组和属性的 npz 存档。我建议查看它的代码。 scipy.io.savemat 也可以用 matlab 兼容的格式写一个稀疏矩阵。按照save_npz 模型,我可以用h5py 编写一个稀疏矩阵。
  • save_npz 不保存lildok 格式,因为数据不是数字数组格式。 h5py 也会有这些问题。 coocsr 更适合面向数组的保存。
  • 我怀疑但应该验证所有sparse 类都依赖于继承的.__reduce__,因此与大多数用户定义的类相同。
猜你喜欢
  • 2015-04-14
  • 1970-01-01
  • 2012-11-24
  • 1970-01-01
  • 2014-09-15
  • 2012-07-24
  • 2014-08-13
  • 2021-10-25
  • 1970-01-01
相关资源
最近更新 更多