我有一个NumPy数组,它只由0和1元素组成,如下所示:
import numpy as np
data = np.array([[1, 1 , 0 , 0 , 0 , 0 , 1 , 0],
[1, 1 , 1 , 1 , 1 , 1 , 1 , 0],
[1, 1 , 1 , 1 , 1 , 1 , 1 , 0],
[0, 0 , 1 , 1 , **1** , 1 , 1 , 0],
[0, 0 , 1 , 1 , 1 , 1 , 1 , 1],
[1, 1 , 1 , 1 , 1 , 1 , 1 , 0],
[1, 1 , 0 , 0 , 0 , 0 , 0 , 0]])
我必须找出元素1的索引,该元素在每个方向上由2乘2的像素中的1包围。
预期答案的位置以粗体显示。
我正在寻找更简单、更快的方法。
您可以使用一些signal processing
-
import numpy as np
from scipy import signal
# Input
data = np.array([[1, 1 , 0 , 0 , 0 , 0 , 1 , 0],
[1, 1 , 1 , 1 , 1 , 1 , 1 , 0],
[1, 1 , 1 , 1 , 1 , 1 , 1 , 0],
[0, 0 , 1 , 1 , 1 , 1 , 1 , 0],
[0, 0 , 1 , 1 , 1 , 1 , 1 , 1],
[1, 1 , 1 , 1 , 1 , 1 , 1 , 0],
[1, 1 , 0 , 0 , 0 , 0 , 0 , 0]])
# Extent of the search
extent = 2;
# Kernel to be used with 2D convolution
kernel = np.ones((2*extent+1,2*extent+1))
# Perform 2D convolution with input data and kernel
filt_out = signal.convolve2d(data, kernel, boundary='symm', mode='same')
# Find where the convolution resulted in a perfect score,
# i.e is equal to the number of elements in kernel
R,C = np.where( filt_out == kernel.size )
输出-
In [66]: print(R,C)
[3] [4]
本节列出了一种使用ndimage
执行与前一种方法相同卷积的替代方法,其余步骤保持不变。以下是获得卷积输出filt_out
-的代码
import scipy.ndimage
filt_out = scipy.ndimage.convolve(data,kernel)
这很容易通过基本的形态学操作:
import numpy as np
from scipy.ndimage.morphology import binary_erosion
data = np.array([[1, 1 , 0 , 0 , 0 , 0 , 1 , 0],
[1, 1 , 1 , 1 , 1 , 1 , 1 , 0],
[1, 1 , 1 , 1 , 1 , 1 , 1 , 0],
[0, 0 , 1 , 1 , 1 , 1 , 1 , 0],
[0, 0 , 1 , 1 , 1 , 1 , 1 , 1],
[1, 1 , 1 , 1 , 1 , 1 , 1 , 0],
[1, 1 , 0 , 0 , 0 , 0 , 0 , 0]])
expected = np.array([[0, 0 , 0 , 0 , 0 , 0 , 0 , 0],
[0, 0 , 0 , 0 , 0 , 0 , 0 , 0],
[0, 0 , 0 , 0 , 0 , 0 , 0 , 0],
[0, 0 , 0 , 0 , 1 , 0 , 0 , 0],
[0, 0 , 0 , 0 , 0 , 0 , 0 , 0],
[0, 0 , 0 , 0 , 0 , 0 , 0 , 0],
[0, 0 , 0 , 0 , 0 , 0 , 0 , 0]])
# otherwise known as np.ones((5, 5))
structuring_element = np.array([[1, 1, 1, 1, 1],
[1, 1, 1, 1, 1],
[1, 1, 1, 1, 1],
[1, 1, 1, 1, 1],
[1, 1, 1, 1, 1]])
# will be of dtype np.bool but you can convert with .astype(np.int)
# if you really need
result = binary_erosion(data, structuring_element)
print(result)
print(np.allclose(result, expected))