![](/img/trans.png)
[英]Most efficient way for decoding 1D array with specific structure to 3D or 4D array (with Python)
[英]What is the most efficient way to extend a dimension of a 4D numpy array?
例如,假设我有一个形状为(2,3,4,5)的数组,我想向其中添加一个(2,3,4,1)数组以生成一个形状为(2,3, 4,6)。
对于大尺寸,最有效的方法是什么?
有什么比dimshuffle和vstack / hstack / dstack更好的东西吗?
(Python 2.7)
以下是各种方法以及随附的基准:
a = np.zeros([100,200,300,5])
b = np.zeros([100,200,300,1])
%timeit c=np.concatenate([a,b],-1)
#1 loops, best of 3: 241 ms per loop
%timeit c=np.vstack([a.T,b.T]).T
#1 loops, best of 3: 309 ms per loop
%timeit c=np.empty([100,200,300,5]); c[...,:5]=a; c[...,5:]=b
#1 loops, best of 3: 311 ms per loop
# Assuming c was already allocated:
%timeit c[...,:5]=a; c[...,5:]=b
#10 loops, best of 3: 113 ms per loop
这些时间都是相当可比的,而且都很慢。 如果所有数组都按转置顺序排列,我们可以做得更好:
va = np.zeros([5,300,200,100])
vb = np.zeros([1,300,200,100])
%timeit vc=np.concatenate([va,vb],0)
#1 loops, best of 3: 191 ms per loop
%timeit vc=np.vstack([va,vb])
#1 loops, best of 3: 284 ms per loop
%timeit vc=np.empty([6,300,200,100]); vc[:5]=va; vc[5:]=vb
#1 loops, best of 3: 281 ms per loop
#Assuming vc is already allocated. This case is somehow
#much faster than the others!
%timeit vc[:5]=va; vc[5:]=vb
#10 loops, best of 3: 26.4 ms per loop
#Somehow the time for allocating vc and for copying the
#values does not add up. I guess this has to do with
#caching working better when the same buffer is reused
%timeit vc=np.empty([6,300,200,100])
#100000 loops, best of 3: 7.73 µs per loop
在fortran中实现相同的操作并通过f2py调用它只会为未转置案例的分配产生大约55 ms的时间。 因此,这些选项似乎都不是效率极低的。 我建议np.concatenate
。 它是通用的,由于某种原因,它比等效的*stack
稍快。 也就是说,除非您可以预分配和重用输出数组,否则在这种情况下,使用广泛分配的分配至少要快2倍。
使用arr.resize(new_shape=(2,3,4,6))
。 这将尝试重新分配原始数组使用的现有内存,因此,它可能比保证返回新分配的数组的任何其他方法快。
缺点是并非总是可以就地执行此操作,在这种情况下,您别无选择,只能创建一个新数组,例如使用numpy.append
。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.