Python 填写numpy数组中超出边界的部分

Python 填写numpy数组中超出边界的部分,python,numpy,indexing,Python,Numpy,Indexing,我不完全确定我该如何命名这个问题。但是我如何才能得到一个numpy数组的一部分,它的一些值在边界之外 请参见下面我的简单示例代码: def get_section(a, center, square_radius): return a[center[0] - square_radius:center[0] + square_radius + 1, \ center[1] - square_radius:center[1] + square_radius + 1

我不完全确定我该如何命名这个问题。但是我如何才能得到一个numpy数组的一部分,它的一些值在边界之外

请参见下面我的简单示例代码:

def get_section(a, center, square_radius):
    return a[center[0] - square_radius:center[0] + square_radius + 1, \
              center[1] - square_radius:center[1] + square_radius + 1]



array = [
    [1, 2, 3, 4, 5, 6, 7, 8, 9],
    [2, 3, 4, 5, 6, 7, 8, 9, 1],
    [3, 4, 5, 0, 7, 8, 9, 1, 2],
    [4, 5, 6, 7, 8, 9, 1, 2, 3],
    [5, 0, 7, 8, 9, 4, 5, 6, 7],
    [6, 7, 8, 9, 1, 2, 3, 4, 5]
]
a = np.asarray(array)
square_radius = 2


center = [2,3]
print(get_section(a, center, square_radius))

center = [4,1]
print(get_section(a, center, square_radius))
假设我有一个数组,但我想通过指定我想要的部分的中心和半径来获得它的一小部分

第一个将打印出:

[[2 3 4 5 6]
 [3 4 5 6 7]
 [4 5 0 7 8]
 [5 6 7 8 9]
 [0 7 8 9 4]]
这正是我想要的。为简单起见,我将“0”放在所识别的两个示例的中心

但是第二个将打印出
[]

对于第二个,我想用-1填充外部值。因此,我希望它返回:

[[-1  3  4  5  0]
 [-1  4  5  6  7]
 [-1  5  0  7  8]
 [-1  6  7  8  9]
 [-1 -1 -1 -1 -1]]

我怎么能在numpy做到这一点呢?

最后!我是用电脑做的。我不确定是否有更好的方法来完成这项工作,因为它非常复杂,但是,它工作得很好:

def get_section(a, center, square_radius):
    tp = max(0, -(center[0] - square_radius))
    bp = max(0, -((a.shape[0]-center[0]-1) - square_radius))
    lp = max(0, -(center[1] - square_radius))
    rp = max(0, -((a.shape[1]-center[1]-1) - square_radius))
    a = np.pad(a, [[tp, bp], [lp, rp]], 'constant', constant_values=-1)
    return a[center[0] - square_radius + tp:center[0] + square_radius + 1 + tp, \
              center[1] - square_radius + lp:center[1] + square_radius + 1 + lp]
并用您的示例进行测试:

>>> center = [2,3]
>>> print(get_section(a, center, square_radius))
[[2 3 4 5 6]
 [3 4 5 6 7]
 [4 5 0 7 8]
 [5 6 7 8 9]
 [0 7 8 9 4]]
>>> center = [4,1]
>>> print(get_section(a, center, square_radius))
[[-1  3  4  5  0]
 [-1  4  5  6  7]
 [-1  5  0  7  8]
 [-1  6  7  8  9]
 [-1 -1 -1 -1 -1]]

为什么?

首先,让我们定义一个数组来测试
np.pad()
函数:

>>> a
array([[1, 2],
       [3, 4]])
然后我们可以快速演示填充是如何工作的,从这个例子中,它应该是不言自明的:

>>> np.pad(a, [[1, 2], [0, 3]], 'constant', constant_values=-1)
array([[-1, -1, -1, -1, -1],
       [ 1,  2, -1, -1, -1],
       [ 3,  4, -1, -1, -1],
       [-1, -1, -1, -1, -1],
       [-1, -1, -1, -1, -1]])
所以我们现在知道,我们可以将
-1s
添加到我们想要的任何边上,我们现在只需要确定我们是否这样做(正方形与边重叠,如第二个示例所示),如果这样,我们需要向每个边添加多少
-1s

这些填充距离是在函数的顶部定义的(
tp
bp
,…用于顶部衬垫,底部衬垫…),我们通过计算得出

计算基本上只需计算边缘和中心之间的距离,然后减去
平方半径
。然而,如果我们将其保持在这个位置,那么我们通常会得到负的填充距离(在半径小于到边缘的距离的情况下,为了解决这个问题,我们只使用
max()
函数和
0
使填充距离仅为正(需要填充)或
0
(该边上不需要填充)

然后,定义了所有这些,我们就用这些值调用
a
上的
pad
函数

最后,我们使用原始的“平方提取”技术来获得围绕中心坐标的平方。唯一的区别是,我们需要通过顶部和左侧填充来偏移所有索引。我们需要这样做,就像我们刚刚填充了一个3的左侧填充,那么原本是一个4的中心现在是1美分re的值为1(因为索引从填充边开始)。为了避免这个问题,我们只需通过将填充差异添加到所有索引上来抵消索引


希望你现在就知道了!

是的,我正在努力理解它是如何工作的。有一段艰难的时光lol。我读了一些关于np.pad的信息,我了解了它是如何填充左/右和上/下的。虽然,当你在np.pad函数前后打印“a”时,“a”似乎没有改变。我真的不明白为什么添加tp和lp会这样做k、 我知道这很管用,只是试着去理解。Thanks@user1179317我已经添加了一个解释。我想我明白了。你几乎可以这样认为,返回的值是原始数组边界内的值,然后在该部分添加了填充。只是有点混乱,因为在遵循代码时,似乎是paddi添加了ng,但是您只返回忽略添加的填充的值。@user1179317啊,我知道,
np.pad
的结果被分配回
a
变量,因此被使用。