在数组末尾填充零的更 Pythonic 方法是什么?
def pad(A, length):
...
A = np.array([1,2,3,4,5])
pad(A, 8) # expected : [1,2,3,4,5,0,0,0]
在我的实际用例中,实际上我想将数组填充到最接近的 1024 倍数。例如:1342 => 2048, 3000 => 3072
numpy.pad
模式的
constant
可以满足您的需求,我们可以传递一个元组作为第二个参数来告诉每个尺寸要填充多少个零,例如 (2, 3)
将在左侧填充 2 零右侧有 3 零:
给定
A
为:
A = np.array([1,2,3,4,5])
np.pad(A, (2, 3), 'constant')
# array([0, 0, 1, 2, 3, 4, 5, 0, 0, 0])
还可以通过传递元组的元组作为填充宽度来填充 2D numpy 数组,其格式为
((top, bottom), (left, right))
:
A = np.array([[1,2],[3,4]])
np.pad(A, ((1,2),(2,1)), 'constant')
#array([[0, 0, 0, 0, 0], # 1 zero padded to the top
# [0, 0, 1, 2, 0], # 2 zeros padded to the bottom
# [0, 0, 3, 4, 0], # 2 zeros padded to the left
# [0, 0, 0, 0, 0], # 1 zero padded to the right
# [0, 0, 0, 0, 0]])
对于您的情况,您指定左侧为零,右侧垫根据模除法计算:
B = np.pad(A, (0, 1024 - len(A)%1024), 'constant')
B
# array([1, 2, 3, ..., 0, 0, 0])
len(B)
# 1024
对于更大的
A
:
A = np.ones(3000)
B = np.pad(A, (0, 1024 - len(A)%1024), 'constant')
B
# array([ 1., 1., 1., ..., 0., 0., 0.])
len(B)
# 3072
对于您的用例,您可以使用 resize() 方法:
A = np.array([1,2,3,4,5])
A.resize(8)
这会调整
A
的大小。如果有对 A
的引用,numpy 会抛出一个 vale 错误,因为引用的值也会更新。要允许此操作,请添加 refcheck=False
选项。
文档指出缺失值将是
0
:
扩大数组:如上所述,但缺失的条目用零填充
供将来参考:
def zeropad(A, size):
t = size - len(A)
return np.pad(A, pad_width=(0, t), mode='constant')
zeropad([1,2,3], 8) # [1 2 3 0 0 0 0 0]
注意:对于 n 维版本,请参阅对 numpy n 维数组进行零填充:
def zeropad(arr, shape):
return np.pad(arr, [(0, max(s - dim, 0)) for s, dim in zip(shape, arr.shape)], mode='constant', constant_values=0)
numpy.pad
:
>>> A = np.array([1,2,3,4,5])
>>> npad = 8 - len(A)
>>> np.pad(A, pad_width=npad, mode='constant', constant_values=0)[npad:]
array([1, 2, 3, 4, 5, 0, 0, 0])
在一个函数中:
def pad(A, npads):
_npads = npads - len(A)
return np.pad(A, pad_width=_npads, mode='constant', constant_values=0)[_npads:]
有
np.pad
:
A = np.array([1, 2, 3, 4, 5])
A = np.pad(A, (0, length), mode='constant')
根据您的用例,所需填充的零数量可以计算为
length = len(A) + 1024 - 1024 % len(A)
。
这应该有效:
def pad(A, length):
arr = np.zeros(length)
arr[:len(A)] = A
return arr
如果初始化一个空数组(np.empty(length)
)然后分别填充
A
和zeros
,你可能能够获得稍微更好的性能,但我怀疑加速是否值得额外的代码复杂性大多数情况。为了获得要填充的值,我想你可能会使用类似
divmod
:的东西
n, remainder = divmod(len(A), 1024)
n += bool(remainder)
基本上,这只是计算出 1024 除以数组长度的次数(以及该除法的余数是多少)。 如果没有余数,那么您只需要
n * 1024
个元素。 如果还有余数,那么你想要
(n + 1) * 1024
。全体:
def pad1024(A):
n, remainder = divmod(len(A), 1024)
n += bool(remainder)
arr = np.zeros(n * 1024)
arr[:len(A)] = A
return arr