10.2 NumPy 专用的二进制文件格式


文档摘要

10.2 NumPy 专用的二进制文件格式 10.2 NumPy 专用的二进制文件格式 10.2.1 格式:存储单个数组 文件格式用于存储单个 NumPy 数组。 它包含数组的元数据(例如形状、数据类型)以及数组的原始数据。 优势: 效率: 二进制格式比文本格式更紧凑,读取和写入速度更快。 精度: 保持数组的原始数据类型和精度,避免了文本格式可能引入的舍入误差。 平台无关性: 文件可以在不同的操作系统和硬件平台上读取。 基本操作: 保存数组到 文件: 使用 函数。 从 文件加载数组: 使用 函数。 代码示例: 输出: 代码详解: : 将数组 保存到名为 的文件中。 第一个参数是文件名(包括扩展名 ),第二个参数是要保存的数组。 : 从名为 的文件中加载数组。 函数返回加载的数组。

10.2 NumPy 专用的二进制文件格式

10.2 NumPy 专用的二进制文件格式

10.2.1 .npy 格式:存储单个数组

.npy 文件格式用于存储单个 NumPy 数组。 它包含数组的元数据(例如形状、数据类型)以及数组的原始数据。

优势:

  • 效率: 二进制格式比文本格式更紧凑,读取和写入速度更快。

  • 精度: 保持数组的原始数据类型和精度,避免了文本格式可能引入的舍入误差。

  • 平台无关性: .npy 文件可以在不同的操作系统和硬件平台上读取。

基本操作:

  • 保存数组到 .npy 文件: 使用 numpy.save() 函数。

  • .npy 文件加载数组: 使用 numpy.load() 函数。

代码示例:

import numpy as np # 创建一个 NumPy 数组 arr = np.arange(10) print("原始数组:\n", arr) # 将数组保存到 .npy 文件 np.save('my_array.npy', arr) # 从 .npy 文件加载数组 loaded_arr = np.load('my_array.npy') print("\n从 .npy 文件加载的数组:\n", loaded_arr) # 验证加载的数组与原始数组是否相同 print("\n数组是否相同:", np.array_equal(arr, loaded_arr))

输出:

原始数组: [0 1 2 3 4 5 6 7 8 9] 从 .npy 文件加载的数组: [0 1 2 3 4 5 6 7 8 9] 数组是否相同: True

代码详解:

  1. np.save('my_array.npy', arr): 将数组 arr 保存到名为 my_array.npy 的文件中。 第一个参数是文件名(包括扩展名 .npy),第二个参数是要保存的数组。

  2. loaded_arr = np.load('my_array.npy'): 从名为 my_array.npy 的文件中加载数组。 np.load() 函数返回加载的数组。

  3. np.array_equal(arr, loaded_arr): 比较原始数组 arr 和加载的数组 loaded_arr 是否相等。 返回 True 如果两个数组的形状和元素都相同,否则返回 False

10.2.2 .npz 格式:存储多个数组

.npz 文件格式用于存储多个 NumPy 数组。 实际上,它是一个 ZIP 压缩文件,其中包含多个 .npy 文件,每个文件对应一个数组。

优势:

  • 组织性: 允许将多个相关的数组存储在一个文件中,方便管理。

  • 压缩: 可以选择使用压缩来减小文件大小,特别是对于包含大量重复数据的数组。

基本操作:

  • 保存多个数组到 .npz 文件: 使用 numpy.savez()numpy.savez_compressed() 函数。

  • .npz 文件加载数组: 使用 numpy.load() 函数,它返回一个类似于字典的对象,其中键是数组的名称,值是对应的数组。

代码示例:

import numpy as np # 创建多个 NumPy 数组 arr1 = np.arange(5) arr2 = np.random.rand(3, 3) arr3 = np.array(['apple', 'banana', 'cherry']) print("数组 1:\n", arr1) print("\n数组 2:\n", arr2) print("\n数组 3:\n", arr3) # 将多个数组保存到 .npz 文件 np.savez('my_arrays.npz', array1=arr1, array2=arr2, array3=arr3) # 从 .npz 文件加载数组 loaded_data = np.load('my_arrays.npz') # 访问加载的数组 loaded_arr1 = loaded_data['array1'] loaded_arr2 = loaded_data['array2'] loaded_arr3 = loaded_data['array3'] print("\n从 .npz 文件加载的数组 1:\n", loaded_arr1) print("\n从 .npz 文件加载的数组 2:\n", loaded_arr2) print("\n从 .npz 文件加载的数组 3:\n", loaded_arr3) # 验证加载的数组与原始数组是否相同 print("\n数组 1 是否相同:", np.array_equal(arr1, loaded_arr1)) print("\n数组 2 是否相同:", np.array_equal(arr2, loaded_arr2)) print("\n数组 3 是否相同:", np.array_equal(arr3, loaded_arr3)) # 关闭 .npz 文件 loaded_data.close()

输出:

数组 1: [0 1 2 3 4] 数组 2: [[0.09419598 0.58385816 0.44326681] [0.14875413 0.7984742 0.86786907] [0.91855299 0.35566135 0.48999822]] 数组 3: ['apple' 'banana' 'cherry'] 从 .npz 文件加载的数组 1: [0 1 2 3 4] 从 .npz 文件加载的数组 2: [[0.09419598 0.58385816 0.44326681] [0.14875413 0.7984742 0.86786907] [0.91855299 0.35566135 0.48999822]] 从 .npz 文件加载的数组 3: ['apple' 'banana' 'cherry'] 数组 1 是否相同: True 数组 2 是否相同: True 数组 3 是否相同: True

代码详解:

  1. np.savez('my_arrays.npz', array1=arr1, array2=arr2, array3=arr3): 将多个数组保存到名为 my_arrays.npz 的文件中。 每个数组都通过关键字参数指定,关键字成为 .npz 文件中对应数组的名称。

  2. loaded_data = np.load('my_arrays.npz'): 从名为 my_arrays.npz 的文件中加载数组。 np.load() 函数返回一个 NpzFile 对象,它类似于一个字典。

  3. loaded_arr1 = loaded_data['array1']: 使用数组的名称(在 np.savez() 中指定的关键字)从 NpzFile 对象中访问数组。

  4. loaded_data.close(): 关闭 .npz 文件。 虽然通常会自动关闭,但显式关闭可以确保资源得到正确释放,特别是当处理大型文件时。

压缩 .npz 文件:

可以使用 numpy.savez_compressed() 函数来保存压缩的 .npz 文件。

import numpy as np # 创建多个 NumPy 数组 arr1 = np.arange(5) arr2 = np.random.rand(3, 3) # 将多个数组保存到压缩的 .npz 文件 np.savez_compressed('my_arrays_compressed.npz', array1=arr1, array2=arr2) # 从压缩的 .npz 文件加载数组 loaded_data = np.load('my_arrays_compressed.npz') # 访问加载的数组 loaded_arr1 = loaded_data['array1'] loaded_arr2 = loaded_data['array2'] print("加载的数组 1:\n", loaded_arr1) print("\n加载的数组 2:\n", loaded_arr2) loaded_data.close()

numpy.savez_compressed() 函数的工作方式与 numpy.savez() 类似,但它使用压缩算法来减小文件大小。

10.2.3 .npy.npz 的内部结构

虽然通常不需要直接操作 .npy.npz 文件的内部结构,但了解它们可以帮助更好地理解 NumPy 如何存储数据。

.npy 文件结构:

.npy 文件包含以下部分:

  1. Magic string: 一个用于标识文件为 NumPy .npy 文件的字符串 (\x93NUMPY).

  2. Version number: 一个表示 .npy 文件格式版本的数字。

  3. Header: 一个 Python 字典,包含数组的形状 (shape)、数据类型 (dtype) 和 fortran_order 标志(指示数组是否以 Fortran 顺序存储)。 此字典以文本形式存储,并使用 ast.literal_eval() 安全地解析。

  4. Data: 数组的原始二进制数据。

.npz 文件结构:

.npz 文件是一个 ZIP 归档文件,其中包含:

  1. 一个或多个 .npy 文件,每个文件对应一个数组。

  2. 可选的 __globals__.pkl 文件,用于存储全局变量(不常用)。

10.2.4 使用场景和最佳实践

  • 大型数据集: 当需要存储和加载大型 NumPy 数组时,.npy.npz 格式是理想的选择。

  • 数据持久化: 它们可以用于将 NumPy 数组保存到磁盘,以便以后使用。

  • 数据交换: 可以在不同的 Python 环境或程序之间交换 NumPy 数组数据。

  • 选择合适的格式: 如果只需要存储单个数组,请使用 .npy 格式。 如果需要存储多个相关的数组,请使用 .npz 格式。

  • 压缩: 对于包含大量重复数据的数组,使用 numpy.savez_compressed() 可以显著减小文件大小。

  • 关闭文件: 始终在使用完 .npz 文件后关闭它,以释放资源。

10.2.5 总结

NumPy 专用的二进制文件格式 .npy.npz 提供了一种高效、精确和平台无关的方式来存储和加载 NumPy 数组数据。 通过 numpy.save(), numpy.load(), numpy.savez()numpy.savez_compressed() 函数,可以轻松地将数组保存到磁盘并从磁盘加载数组。 了解这些格式的内部结构可以帮助更好地理解 NumPy 如何处理数据存储。在处理大型数据集时,选择合适的格式和使用压缩可以显著提高效率和节省存储空间。

10.2.6 图示

这个图示概括了使用 .npy.npz 文件格式存储和加载 NumPy 数组的流程。 它帮助理解在不同情况下应该使用哪个函数,以及如何访问加载的数据。


发布者: 作者: 转发
评论区 (0)
U