Numpy字符串数组填充字符串

时间:2018-03-01 12:34:59

标签: python string python-3.x numpy

我创建了一个2d Numpy字符串数组,如下所示:

a = np.full((2, 3), '#', dtype=np.unicode)
print(a)

输出结果为:

array([['#', '#', '#'], ['#', '#', '#']], dtype=`'<U1'`)

我想用&#39;填充它?&#39;在宽度为1的所有边上。我希望输出为:

array([
['?', '?', '?', '?', '?'],
['?', '#', '#', '#', '?'],
['?', '#', '#', '#', '?'],
['?', '#', '#', '#', '?'],
['?', '?', '?', '?', '?']],
dtype=`'<U1')

我尝试了以下内容:

b = np.pad(a, ((1, 1), (1, 1)), 'constant', constant_values=(('?', '?'), ('?', '?')))

但是这会产生以下错误:

File "<stdin>", line 1, in <module>
File "/usr/lib/python3/dist-packages/numpy/lib/arraypad.py", line 1357, in pad
    cast_to_int=False)
File "/usr/lib/python3/dist-packages/numpy/lib/arraypad.py", line 1069, in _normalize_shape
    return tuple(tuple(axis) for axis in arr.tolist())
AttributeError: 'tuple' object has no attribute 'tolist'

类似的代码适用于整数。我对字符串做错了什么?

2 个答案:

答案 0 :(得分:2)

您无法使用字符串文字填充数组。相反,如文档中所述,您可以使用pad_with函数,如下所示:

In [79]: def pad_with(vector, pad_width, iaxis, kwargs):
    ...:     pad_value = kwargs.get('padder', '?')
    ...:     vector[:pad_width[0]] = pad_value
    ...:     vector[-pad_width[1]:] = pad_value
    ...:     return vector
    ...: 

In [80]: 

In [80]: np.pad(a, 1, pad_with)
Out[80]: 
array([['?', '?', '?', '?', '?'],
       ['?', '#', '#', '#', '?'],
       ['?', '#', '#', '#', '?'],
       ['?', '#', '#', '#', '?'],
       ['?', '?', '?', '?', '?']], dtype='<U1')

请注意,在pad_value = kwargs.get('padder', '?')函数的行pad_with中,如果np.pad的调用者没有提供填充参数,则应使用默认填充值。您将预期的padder作为关键字参数传递给函数。

In [82]: np.pad(a, 1, pad_with, padder='*')
Out[82]: 
array([['*', '*', '*', '*', '*'],
       ['*', '#', '#', '#', '*'],
       ['*', '#', '#', '#', '*'],
       ['*', '#', '#', '#', '*'],
       ['*', '*', '*', '*', '*']], dtype='<U1')

答案 1 :(得分:0)

即使您可以pad工作,也可以更快地将a插入空白bpad是针对复杂的填充模式设置的,并且逐行地逐行完成作业。

In [29]: a = np.full((2,3),'#')
In [30]: a
Out[30]: 
array([['#', '#', '#'],
       ['#', '#', '#']], dtype='<U1')
In [31]: b = np.full((4,5),'?')
In [32]: b
Out[32]: 
array([['?', '?', '?', '?', '?'],
       ['?', '?', '?', '?', '?'],
       ['?', '?', '?', '?', '?'],
       ['?', '?', '?', '?', '?']], dtype='<U1')
In [33]: b[1:-1,1:-1] = a
In [34]: b
Out[34]: 
array([['?', '?', '?', '?', '?'],
       ['?', '#', '#', '#', '?'],
       ['?', '#', '#', '#', '?'],
       ['?', '?', '?', '?', '?']], dtype='<U1')

这是一个聪明的pad_with解决方案,添加了一个印刷品,因此我们可以看到它被调用的频率:

In [36]: def pad_with(vector, pad_width, iaxis, kwargs):
    ...:     ...:     print(vector)
    ...:     ...:     pad_value = kwargs.get('padder', '?')
    ...:     ...:     vector[:pad_width[0]] = pad_value
    ...:     ...:     vector[-pad_width[1]:] = pad_value
    ...:     ...:     return vector
    ...: 
In [37]: np.pad(a,1,pad_with)
['' '' '' '']
['' '#' '#' '']
['' '#' '#' '']
['' '#' '#' '']
['' '' '' '']
['?' '?' '?' '?' '?']
['' '#' '#' '#' '']
['' '#' '#' '#' '']
['?' '?' '?' '?' '?']
Out[37]: 
array([['?', '?', '?', '?', '?'],
       ['?', '#', '#', '#', '?'],
       ['?', '#', '#', '#', '?'],
       ['?', '?', '?', '?', '?']], dtype='<U1')