0

我正在尝试检查矩阵中元素邻域的元素之间的差异是否大于某个容差值,如果是,则在新矩阵中邻域元素的相同索引处给出 1 的值. 不知何故,我总是在新矩阵中得到所有的结果,这是错误的。这是我的代码。另外,我通过将图片转换为矩阵来获得矩阵。

from PIL import Image
import numpy as np
from numpy.lib.stride_tricks import as_strided


imo = Image.open("/home/gauss/Pictures/images.jpg")


matrix_pic = np.array(imo.convert('L')).astype(float)
dim = matrix_pic.shape


# start 1 step out of the outer borders of the matrix


def binary_edges(pic_mat , tolerance):  
    dim = pic_mat.shape
    binary_mat = np.zeros((dim[0],dim[1]))
    for i in range(1  , dim[0]-1):
        for j in range(1  ,dim[1]-1):
            center = pic_mat[i,j]
            if (abs(pic_mat[i+1,j] - center ) > tolerance):
                binary_mat[i+1,j] = 1
            if (abs(pic_mat[i,j+1] - center ) > tolerance):
                binary_mat[i,j+1] = 1
            if (abs(pic_mat[i+1,j+1] - center ) > tolerance):
                binary_mat[i+1,j+1] = 1
            if (abs(pic_mat[i-1,j] - center ) > tolerance):
                binary_mat[i-1,j] = 1
            if (abs(pic_mat[i,j-1] - center ) > tolerance):
                binary_mat[i,j-1] = 1
            if (abs(pic_mat[i-1,j-1] - center ) > tolerance):
                binary_mat[i-1,j-1] = 1
    return binary_mat       

myarray = binary_edges(matrix_pic, 60)
im = Image.fromarray(myarray)
im.show()
4

1 回答 1

0

编辑:不知道我是如何错过多年前发布的,哦,好吧,为了那些关注的人,我会留下这个答案。

根据评论,您似乎已经解决了一个问题,但是在我看来,您的函数 binary_edges 以另一种方式不符合您的预期目的。

def binary_edges(pic_mat , tolerance):  
    dim = pic_mat.shape
    binary_mat = np.zeros((dim[0],dim[1]))
    for i in range(1  , dim[0]-1):
        for j in range(1  ,dim[1]-1):
            center = pic_mat[i,j]
            if (abs(pic_mat[i+1,j] - center ) > tolerance):
                binary_mat[i+1,j] = 1
            if (abs(pic_mat[i,j+1] - center ) > tolerance):
                binary_mat[i,j+1] = 1
            if (abs(pic_mat[i+1,j+1] - center ) > tolerance):
                binary_mat[i+1,j+1] = 1
            if (abs(pic_mat[i-1,j] - center ) > tolerance):
                binary_mat[i-1,j] = 1
            if (abs(pic_mat[i,j-1] - center ) > tolerance):
                binary_mat[i,j-1] = 1
            if (abs(pic_mat[i-1,j-1] - center ) > tolerance):
                binary_mat[i-1,j-1] = 1
            #If I understand your intention correctly, then I think you're missing these two lines (notice that each element should have 8 neighbours)
            if (abs(pic_mat[i+1,j-1] - center ) > tolerance):
                binary_mat[i+1,j-1] = 1
            if (abs(pic_mat[i-1,j+11] - center ) > tolerance):
                binary_mat[i-1,j+11] = 1
    return binary_mat  

我是否可以建议一种替代方法,该方法对于合理大小的 pic_mat 矩阵将显着加快,并且在我看来,它的混乱程度更低。

def binary_edges_np(pic_mat, tolerance):
    dim = pic_mat.shape
    binary_mat = np.zeros((dim[0],dim[1]), dtype=bool)
    for i,j in [0,1],[1,0],[1,1],[1,-1]:
        s = pic_mat.shape
        slice1 = np.s_[max(0, 0+i):s[0]+i, max(0+j,0):s[1]+j]
        slice2 = np.s_[max(0-i,0):s[0]-i, max(0-j,0):s[1]-j]
        bool_slice = np.abs(pic_mat[slice1] - pic_mat[slice2]) > tolerance
        binary_mat[slice1] += bool_slice
        binary_mat[slice2] += bool_slice
    return binary_mat

如下:

matrix_pic = np.random.randint(0,255, (1000,1000))
s = time.time()
a = binary_edges(matrix_pic, 60)
print("binary_edges:", time.time() - s)
s = time.time()
b = binary_edges_np(matrix_pic, 60)
print("binary_edges_np:", time.time() - s)

binary_edges:5.694662809371948,binary_edges_np:0.01562666893005371

此外,请注意,您的原始函数肯定具有边界效应,其中边缘的 2 行/列内的元素不会被正确标记为超过阈值,我认为这不是故意的。新方法也为边缘提供了正确的值:

print((a == b).all()) # = False
print((a[2:-2,2:-2] == b[2:-2,2:-2]).all()) # True
于 2021-05-05T15:13:26.063 回答