Reputation: 5875
What's the most efficient way to pad an array of matrices with zeros?
example:
# Lets construct an array of 2 matrices from 3 arrays of vectors
import numpy as np
A = np.array([[0,1,2],[3,4,5]]) # 2 vectors
B = np.array([[6,7,8],[9,10,11]]) # 2 vectors
C = np.array([[12,13,14],[15,16,17]]) # 2 vectors
M = np.dstack((A,B,C))
'''
# Result: array([[[ 0, 6, 12],
[ 1, 7, 13],
[ 2, 8, 14]],
[[ 3, 9, 15],
[ 4, 10, 16],
[ 5, 11, 17]]]) #
'''
I want to add a column and/or a row of zeros to every matrix element in the array such as:
'''
# Result: array([[[ 0, 6, 12, 0],
[ 1, 7, 13, 0],
[ 2, 8, 14, 0],
[ 0, 0, 0, 0]],
[[ 3, 9, 15, 0],
[ 4, 10, 16, 0],
[ 5, 11, 17, 0]
[ 0, 0, 0, 0]]]) #
'''
Upvotes: 0
Views: 3979
Reputation: 231375
np.pad
will work, but for this case it is overkill. We can do it directly with:
A sample 3d array (different dimensions make changes more obvious)
In [408]: M=np.arange(2*3*4).reshape((2,3,4))
In [409]: M
Out[409]:
array([[[ 0, 1, 2, 3],
[ 4, 5, 6, 7],
[ 8, 9, 10, 11]],
[[12, 13, 14, 15],
[16, 17, 18, 19],
[20, 21, 22, 23]]])
A blank array of the desired target shape
In [410]: M1=np.zeros((2,4,5),M.dtype)
Copy values from M
to the target in the right slice range.
In [411]: M1[:,:-1,:-1]=M
In [412]: M1
Out[412]:
array([[[ 0, 1, 2, 3, 0],
[ 4, 5, 6, 7, 0],
[ 8, 9, 10, 11, 0],
[ 0, 0, 0, 0, 0]],
[[12, 13, 14, 15, 0],
[16, 17, 18, 19, 0],
[20, 21, 22, 23, 0],
[ 0, 0, 0, 0, 0]]])
A copy like this is required. There's no way of expanding the size of M
itself. pad
returns a new array as well, having performed a general version of this allocate and copy. So there isn't much of an efficiency issue.
You could also concatenate (or 'append') a 0 row or column in the right dimensions. But what I've illustrated does it in one step.
Upvotes: 2
Reputation: 65430
You're going to want to use numpy.pad
to do this. You can use the second input argument to specify the amount to pad before and after the data in each of the dimensions of the array. Then specify a constant padding type where the padding value is 0 (the default).
result = numpy.pad(M, ((0,0),(0,1),(0,1)), 'constant', constant_values=0)
array([[[ 0, 6, 12, 0],
[ 1, 7, 13, 0],
[ 2, 8, 14, 0],
[ 0, 0, 0, 0]],
[[ 3, 9, 15, 0],
[ 4, 10, 16, 0],
[ 5, 11, 17, 0],
[ 0, 0, 0, 0]]])
Upvotes: 1