Numpy之pad用法
- 1、函数说明
-
- 1.1、语法
- 1.2、参数解释
- 2、一、二维数组填充
-
- 2.1、一维数组填充
- 2.2、二维数组填充
- 3、三维数组填充
-
- 3.1、通道在前[CHW]
- 3.2、通道在后[HWC]
- 4、四维数组填充
-
- 4.1、通道在前 BCHW
- 4.2、通道在后 BHWC
- 5、总结
1、函数说明
1.1、语法
numpy.pad(array, pad_width, mode=‘constant’, **kwargs)
1.2、参数解释
array:需要填充的数组
pad_width:填充尺寸,按轴填充,每个轴前后两侧的填充数量组成一个tuple。
mode:填充方式,默认是常量填充。
2、一、二维数组填充
2.1、一维数组填充
一维数组填充很简单,
pad_width
是一个包含两个整数的元组,代表在数组左右两侧填充的数据个数,
“constant”
表示常量,默认为0,可以使用
"constant_values"
自定义填充值。
a=np.array([1,2,10])
b=np.pad(a,(2,4),"constant")
array([ 0, 0, 1, 2, 10, 0, 0, 0, 0])
array([ 1, 1, 1, 2, 10, 1, 1, 1, 1])
2.2、二维数组填充
先定义一个2x2的二维数组
array([[1, 2],
[4, 9]])
为了能直观的看到
pad_width
参数如何设置,我们让二维数组的行方向上的上侧扩充2行,下侧扩充4行,列方向上的左侧扩充1列,右侧扩充3列,此时
pad_width=((2,4)(1,3))
,填充值为-100。
扩充结果
array([[-100, -100, -100, -100, -100, -100],
[-100, -100, -100, -100, -100, -100],
[-100, 1, 2, -100, -100, -100],
[-100, 4, 9, -100, -100, -100],
[-100, -100, -100, -100, -100, -100],
[-100, -100, -100, -100, -100, -100],
[-100, -100, -100, -100, -100, -100],
[-100, -100, -100, -100, -100, -100]])
这个例子中pad_width=((2,4),(1,3)),其中(2,4)代表在第一个轴(行)上的扩充数,(1,3)代表第二个轴(列)上的扩充数。
3、三维数组填充
3.1、通道在前[CHW]
定义一个通道在前的三维数组,通道数为3,高为2,宽为2,类似一张2x2尺寸的RGB图像。
array([[[1, 2],
[4, 9]],
[[3, 2],
[7, 4]],
[[1, 9],
[0, 3]]])
这里我们让图片的前后左右各扩充一个像素,与二维数组不同的是,我们希望三个通道能同时进行扩充,此时,
pad_width=((0,0),(1,1),(1,1))
。
array([[[-100, -100, -100, -100],
[-100, 1, 2, -100],
[-100, 4, 9, -100],
[-100, -100, -100, -100]],
[[-100, -100, -100, -100],
[-100, 3, 2, -100],
[-100, 7, 4, -100],
[-100, -100, -100, -100]],
[[-100, -100, -100, -100],
[-100, 1, 9, -100],
[-100, 0, 3, -100],
[-100, -100, -100, -100]]])
这个例子中pad_width=((0,0),(1,1),(1,1)),其中(0,0)代表在第一个轴(通道)上的扩充数,(1,1)代表第二个轴(行)上的扩充数,下一个(1,1)代表第三个轴(列)上的扩充数。
注意通道位置上的扩充参数(0,0)不能省略。
3.2、通道在后[HWC]
同样一张2x2的RGB图像,我们用通道在后的数组形式来表示,(通道在后的数组的表达形式不如通道在前的数组直观,可以用
transpose()
方法将通道在前的数组转换为通道在后的数组)
array([[[1, 3, 1],
[2, 2, 9]],
[[4, 7, 0],
[9, 4, 3]]])
通道轴上不需要扩充,因此设置为(0,0),通道顺序在最后,此时的
pad_width=((1,1),(1,1),(0,0))
array([[[-100, -100, -100],
[-100, -100, -100],
[-100, -100, -100],
[-100, -100, -100]],
[[-100, -100, -100],
[ 1, 3, 1],
[ 2, 2, 9],
[-100, -100, -100]],
[[-100, -100, -100],
[ 4, 7, 0],
[ 9, 4, 3],
[-100, -100, -100]],
[[-100, -100, -100],
[-100, -100, -100],
[-100, -100, -100],
[-100, -100, -100]]])
如果你对通道在后的数组表示形式很难理解,就不太能够从上面的输出结果判断我们的填充操作是否正确,可以使用
transpose()
方法,把扩充后的数组的通道顺序转换到前面,
array([[[-100, -100, -100, -100],
[-100, 1, 2, -100],
[-100, 4, 9, -100],
[-100, -100, -100, -100]],
[[-100, -100, -100, -100],
[-100, 3, 2, -100],
[-100, 7, 4, -100],
[-100, -100, -100, -100]],
[[-100, -100, -100, -100],
[-100, 1, 9, -100],
[-100, 0, 3, -100],
[-100, -100, -100, -100]]])
此时可以看到,确实在每个通道的前后左右都扩充了一个像素。
4、四维数组填充
深度学习模型的输入通常是4个维度,即B,C,H,W,分别对应批量,通道,高度,宽度。一般情况下如果图片需要做
pad()
操作,都是在单张图片上先填充,然后再合并在一起,这里我们为了测试numpy的
pad()
方法,也在4维数组上做下测试,同样分通道在前和在后的情况。(批量维度的位置始终不变)。
4.1、通道在前 BCHW
先按照BCHW的顺序定义一个四维数组,这里我们设置B=2,C=3,H=2,W=2,类似两张2X2的RGB图像。
aaaa=np.array([[[[1,2],[4,9]],[[3,2],[7,4]],[[1,9],[0,3]]],[[[2,2],[4,3]],[[1,2],[4,4]],[[4,9],[0,2]]]])
print(aaaa)
[[[[1 2]
[4 9]]
[[3 2]
[7 4]]
[[1 9]
[0 3]]]
[[[2 2]
[4 3]]
[[1 2]
[4 4]]
[[4 9]
[0 2]]]]
我们现在是对4维数组做扩充,增加的一维是batch_size,这个维度不需要扩充,因此扩充参数设置为(0,0),此时
pad_width=((0,0),(0,0),(1,1),(1,1))
。
bbbb=np.pad(aaaa,((0,0),(0,0),(1,1),(1,1)),"constant",constant_values=-100)
print(bbbb)
[[[[-100 -100 -100 -100]
[-100 1 2 -100]
[-100 4 9 -100]
[-100 -100 -100 -100]]
[[-100 -100 -100 -100]
[-100 3 2 -100]
[-100 7 4 -100]
[-100 -100 -100 -100]]
[[-100 -100 -100 -100]
[-100 1 9 -100]
[-100 0 3 -100]
[-100 -100 -100 -100]]]
[[[-100 -100 -100 -100]
[-100 2 2 -100]
[-100 4 3 -100]
[-100 -100 -100 -100]]
[[-100 -100 -100 -100]
[-100 1 2 -100]
[-100 4 4 -100]
[-100 -100 -100 -100]]
[[-100 -100 -100 -100]
[-100 4 9 -100]
[-100 0 2 -100]
[-100 -100 -100 -100]]]]
4.2、通道在后 BHWC
请读者自己尝试写一下如何扩充,用来检验是否理解了NumPy的
pad()
方法。
5、总结
1、pad()`方法中最关键的参数是pad_width,pad_width的形式是一个嵌套元组,即内部元素为元组的元组,((before_1,end_1),(before_2,end_2)…(before_N,end_N)),N为数组的维度。
2、在做高维度扩充时要注意不需要填充的轴对应的pad_width的元素为(0,0),且不能省略。