题
我有2D numpy
大批。有没有办法在其中创建一个视图,其中包括第一个 k
行和所有列?
关键是避免复制基础数据(数组太大,以至于制作部分副本是不可行的。)
解决方案
当然,只需像平常一样索引。例如 y = x[:k, :]
这将返回原始数组中的视图。不会复制数据,并且对 y
将反映在 x
反之亦然。
编辑:
我通常使用UINT8的> 10GB 3D阵列,因此我很担心这一点...如果您牢记一些事情,Numpy在内存管理方面可能非常有效。以下是避免在内存中制作数组副本的一些技巧:
利用 +=
, -=
, *=
, 等,以避免制作数组的副本。例如 x += 10
将修改到位的数组, x = x + 10
将复制并修改它。 (还要看看 numexpr)
如果您想与 x = x + 10
, , 意识到 x = x + 10.0
将造成 x
如果还没有,则自动被抛入浮点阵列。然而, x += 10.0
, , 在哪里 x
是整数数组,将导致 10.0
相反,要将其降低到与数组相同精度的INT。
此外,许多Numpy功能都采用 out
参数,因此您可以做类似的事情 np.abs(x, x)
占据绝对价值 x
到位。
作为第二次编辑,这里还有一些有关 视图 VS. 副本 带有Numpy数组:
与python列表不同, y = x[:]
不返回副本,它将返回视图。如果您确实想要一份副本(当然,这是您使用的内存的两倍)使用 y = x.copy()
您通常会听到有关Numpy阵列的“花式索引”。使用列表(或整数数组)作为索引是“花哨的索引”。它可能非常有用,但是复制数据。
作为一个例子: y = x[[0, 1, 2], :]
返回副本, y = x[:3,:]
会返回视图。
甚至真的很疯狂地索引 x[4:100:5, :-10:-1, None]
是“正常”的索引并会返回视图,因此不要害怕在大型阵列上使用各种切片技巧。
x.astype(<dtype>)
将返回数据副本作为新类型,而x.view(<dtype>)
将返回视图。
但是,请注意这一点……它非常强大且有用,但是您需要了解基础数据如何存储在内存中。如果您有一系列的浮子,并将它们视为ints,(反之亦然)numpy将解释基础 位 数组作为ints。
例如,这意味着 1.0
作为一个小型系统上的64位漂浮 4607182418800017408
当被视为64位int时 [ 0, 0, 0, 0, 0, 0, 240, 63]
如果被视为UINT8。当您需要在大型数组上进行某种形式的某种扭转时,这真的很好,但是……您对如何解释内存缓冲区的解释具有低级别的控制。