在本教程中,您将学习如何使用 NumPy reshape() 在不更改原始数据的情况下重塑 NumPy 数组。
使用 Numpy 数组时,您可能经常希望将现有数组重塑为不同维度的数组。 当您在多个步骤中转换数据时,这可能特别有用。
NumPy reshape() 可以帮助您轻松完成。 在接下来的几分钟内,您将学习使用 reshape() 的语法,并将数组重塑为不同的维度。
目录
什么是 NumPy 数组中的重塑?
使用 NumPy 数组时,您可能首先要创建一个一维数字数组。 然后将其重塑为具有所需尺寸的数组。
当新数组的维度最初未知或在执行期间推断时,这特别有用。 或者,某个数据处理步骤也可能要求输入具有特定形状。
这就是重塑派上用场的地方。
例如,考虑下图。 我们有一个向量——一个由 6 个元素组成的一维数组。 我们可以将其重塑为 2×3、3×2、6×1 等形状的数组。
▶️ 要按照本教程中的示例进行操作,您需要安装 Python 和 NumPy。 如果您还没有 NumPy,请查看我们的 NumPy 安装指南。
您现在可以继续并在别名 np 下导入 NumPy,方法是运行: import numpy as np.
让我们继续学习下一节中的语法。
NumPy reshape() 的语法
下面是使用 NumPy reshape() 的语法:
np.reshape(arr, newshape, order="C"|'F'|'A')
- arr 是任何有效的 NumPy 数组对象。 在这里,它是要重塑的阵列。
- newshape 是新数组的形状。 它可以是整数或元组。
- 当 newshape 为整数时,返回的数组是一维的。
- order 是指您希望读取要重新整形的数组元素的顺序。
- 默认值为’C’,这意味着原始数组的元素将以类似C的索引顺序(从0开始)读取
- “F”代表类似 Fortran 的索引(从 1 开始)。 并且“A”根据数组 arr 的内存布局以类似 C 或类似 Fortran 的顺序读取元素。
那么 np.reshape() 返回什么?
如果可能,它会返回原始数组的重塑视图。 否则,它会返回数组的副本。
在上面一行中,我们提到 NumPy reshape() 会尽可能尝试返回视图。 否则,它会返回一个副本。 让我们继续讨论视图和副本之间的区别。
查看与 NumPy 数组的副本
顾名思义,copy 是原始数组的副本。 对副本所做的任何更改都不会影响原始数组。
另一方面,视图只是指原始阵列的重塑视图。 这意味着对视图所做的任何更改也会影响原始数组,反之亦然。
使用 NumPy reshape() 将一维数组重塑为二维数组
#1。 让我们首先使用创建示例数组 np.arange().
我们需要一个包含 12 个数字的数组,从 1 到 12,称为 arr1。 由于 NumPy arange() 函数默认不包括端点,因此将停止值设置为 13。
现在让我们使用上面的语法,将具有 12 个元素的 arr1 重塑为形状为 (4,3) 的二维数组。 让我们将此 arr2 称为 4 行 3 列。
import numpy as np arr1 = np.arange(1,13) print("Original array, before reshaping:n") print(arr1) # Reshape array arr2 = np.reshape(arr1,(4,3)) print("nReshaped array:") print(arr2)
让我们看一下原始数组和重构数组。
Original array, before reshaping: [ 1 2 3 4 5 6 7 8 9 10 11 12] Reshaped array: [[ 1 2 3] [ 4 5 6] [ 7 8 9] [10 11 12]]
除了将数组作为参数 np.reshape() 传递,您还可以在原始数组上调用 .reshape() 方法。
您可以运行 dir(arr1),它将列出您可以在数组对象 arr1 上使用的所有可能的方法和属性。
dir(arr1) # Output [ ... ... 'reshape' ... .. ]
在上面的代码单元中,您可以看到 .reshape() 是在现有 NumPy 数组 arr1 上使用的有效方法。
▶️ 所以,你也可以使用下面的简化语法来重塑 NumPy 数组。
arr.reshape(d0,d1,...,dn) # where: # d0, d1,..,dn are the dimensions of the reshaped array # d0 * d1 * ...* dn = N, the number of elements in arr
对于本教程的其余部分,让我们在示例中使用此语法。
#2。 让我们尝试将我们的 12 元素向量重塑为 12 x 1 数组。
import numpy as np arr1 = np.arange(1,13) print("Original array, before reshaping:n") print(arr1) # Reshape array arr3 = arr1.reshape(12,1) print("nReshaped array:") print(arr3)
在下面的输出中,您可以看到数组已根据需要进行了重新整形。
Original array, before reshaping: [ 1 2 3 4 5 6 7 8 9 10 11 12] Reshaped array: [[ 1] [ 2] [ 3] [ 4] [ 5] [ 6] [ 7] [ 8] [ 9] [10] [11] [12]]
❔ 那么,我们如何检查我们是否获得了副本或视图?
要检查这一点,您可以调用返回数组的基本属性。
- 如果数组是副本,则基本属性将为无。
- 如果数组是视图,则基本属性将是原始数组。
让我们快速验证这一点。
arr3.base # Output array([ 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12])
如您所见, arr3 的 base 属性返回原始数组。 这意味着我们已经收到了原始数组的视图。
#3。 现在,让我们尝试将向量重塑为另一个有效的 2 x 6 数组。
import numpy as np arr1 = np.arange(1,13) print("Original array, before reshaping:n") print(arr1) # Reshape array arr4 = arr1.reshape(2,6) print("nReshaped array:") print(arr4)
这是输出:
Original array, before reshaping: [ 1 2 3 4 5 6 7 8 9 10 11 12] Reshaped array: [[ 1 2 3 4 5 6] [ 7 8 9 10 11 12]]
在下一节中,让我们将 arr1 重塑为 3D 数组。
使用 NumPy reshape() 将 1D 数组重塑为 3D 数组
要将 arr1 重塑为 3D 数组,让我们将所需的维度设置为 (1, 4, 3)。
import numpy as np arr1 = np.arange(1,13) print("Original array, before reshaping:n") print(arr1) # Reshape array arr3D = arr1.reshape(1,4,3) print("nReshaped array:") print(arr3D)
我们现在已经创建了一个与原始数组 arr1 具有相同 12 个元素的 3D 数组。
Original array, before reshaping: [ 1 2 3 4 5 6 7 8 9 10 11 12] Reshaped array: [[[ 1 2 3] [ 4 5 6] [ 7 8 9] [10 11 12]]]
如何在重塑期间调试值错误
如果您还记得语法,那么仅当维度的乘积等于数组中元素的数量时,整形才有效。
import numpy as np arr1 = np.arange(1,13) print("Original array, before reshaping:n") print(arr1) # Reshape array arr2D = arr1.reshape(4,4) print("nReshaped array:") print(arr2D)
在这里,您尝试将一个 12 元素数组重塑为一个 4×4 数组,其中包含 16 个元素。 解释器抛出一个值错误,如下所示。
Original array, before reshaping: [ 1 2 3 4 5 6 7 8 9 10 11 12] ----------------------------------------------------------- ValueError Traceback (most recent call last) <ipython-input-11-63552bcc8c37> in <module>() 6 7 # Reshape array ----> 8 arr2 = arr1.reshape(4,4) 9 print("nReshaped array:") 10 print(arr2) ValueError: cannot reshape array of size 12 into shape (4,4)
为避免此类错误,您可以使用 -1 根据元素总数自动推断其中一个维度的形状。
例如,如果您事先知道 n – 1 个维度,则可以使用 -1 来推断重构数组中的第 n 个维度。
如果您有一个 24 元素的数组,并且您想将其重塑为 3D 数组。 假设您需要 3 行和 4 列。 您可以沿第三个维度传入 -1 的值。
import numpy as np arr1 = np.arange(1,25) print("Original array, before reshaping:n") print(arr1) # Reshape array arr_res = arr1.reshape(4,3,-1) print("nReshaped array:") print(arr_res) print(f"Shape of arr_res:{arr_res.shape}")
当您检查形状数组的形状时,您可以看到重新调整的数组沿第三维的形状为 2。
Original array, before reshaping: [ 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24] Reshaped array: [[[ 1 2] [ 3 4] [ 5 6]] [[ 7 8] [ 9 10] [11 12]] [[13 14] [15 16] [17 18]] [[19 20] [21 22] [23 24]]] Shape of arr_res:(4, 3, 2)
这对于展平阵列特别有用。 您将在下一节中了解这一点。
使用 NumPy reshape() 展平数组
有时您需要从 N 维数组返回到扁平数组。 假设您要将图像展平为一个长的像素向量。
让我们使用以下步骤编写一个简单的示例:
- 生成一个 3 x 3 灰度图像数组 img_arr — 像素范围为 0 到 255。
- 接下来,展平这个 img_arr 并打印出展平的数组 flat_arr。
- 另外,打印出 img_arr 和 flat_arr 的形状进行验证。
img_arr = np.random.randint(0, 255, (3,3)) print(img_arr) print(f"Shape of img_arr: {img_arr.shape}") flat_arr = img_arr.reshape(-1) print(flat_arr) print(f"Shape of flat_arr: {flat_arr.shape}")
这是输出。
[[195 145 77] [ 63 193 223] [215 43 36]] Shape of img_arr: (3, 3) [195 145 77 63 193 223 215 43 36] Shape of flat_arr: (9,)
在上面的代码单元中,您可以看到 flat_arr 是具有 9 个元素的像素值的一维向量。
总结👩🏫
是时候快速回顾一下我们学到的东西了。
- 使用 np.reshape(arr, newshape) 将 arr 重塑为 newshape 中指定的形状。 newshape 是一个元组,指定了重构数组的维度。
- 或者,使用 arr.reshape(d0, d1, …, dn) 将 arr 重塑为形状 d0 x d1 x … x dn
- 检查是否 d0 * d1 * …* dn = N,原始数组中的元素数,以避免在重新整形期间出现值错误。
- 如果您希望自动推断维度,则对新形状中的最多一个维度使用 -1。
- 最后,您可以使用 arr.reshape(-1) 来展平阵列。
现在您知道如何使用 NumPy reshape(),了解 NumPy linspace() 函数的工作原理。
如果您愿意,可以尝试 Jupyter notebook 中的代码示例。 如果您正在寻找其他开发环境,请查看我们的 Jupyter 替代品指南。