模拟了创建图像的角图像的算法,结果不正确。 HALCON软件的sobel_dir运算符将返回方向“角度”图像。我使用Python根据说明重写了该算法,但是我不知道如何计算最终的灰度值。
算法说明: 1.计算图像水平和垂直方向的索贝尔核卷积,即分别获得图像的Ex和Ey 2.根据Ex和Ey,获得幅度图像,即边缘检测图像 3.根据Ex和Ey的正负条件将灰度值分配到指定范围,并生成幅度为Angle
的方向图。第一步和第二步都没有问题,但是我的算法在第三步中不正确。以下是原始文本中对第三步的描述:
———————————————————————————————————————————————— ——————————————————————— 边缘方向以EdgeDirection返回,并以2度的步长存储,即,在数学上为正方向且相对于水平轴为x度的边缘方向在边缘方向图像中存储为x / 2。此外,考虑强度变化的方向。设Ex,Ey表示图像梯度。然后,以下边缘方向返回为r / 2:
强度增加|前/后|
边缘方向r
从下到上| 0 / + | 0 |
从右下到左上| -/ + | ] 0,90 [
从右到左| -/ 0 | 90
从右上方到左下方| -/-| ] 90,180 [
从上到下| -/ 0 | 180
从左上到右下| +/- | ] 180,270 [
从左到右| +/- | 270
从左下到右上| + / + | 180
我知道该算法是将原来的切线角度替换为角度方向,以便更有效地利用角度功能。但是我不知道如何确定0到90之间的灰度值, 90和180.学生:根据幅度?
def sobel_dir(Image, FilterType, Size):
'''
使用Sobel算子检测边缘(振幅和方向)
:param Image: 输入图像
:param FilterType: 过滤器类型
:param Size: 掩码尺寸
:return EdgeAmplitude: 边缘振幅(梯度大小)图像
:return EdgeDirection: 图像边缘方向
'''
Image = Image.astype(np.float_)
hor = np.array([[1, 2, 1], [0, 0, 0], [-1, -2, -1]])
ver = np.array([[1, 0, -1], [2, 0, -2], [1, 0, -1]])
Size = Size * 2 + 1
if Size == 3:
pass
elif Size > 3 and 'binomial' in FilterType:
Image = Binomial2D(Image, Size)
elif Size > 3:
Image = cv2.GaussianBlur(Image, (Size, Size), 0)
s1 = cv2.filter2D(Image, -1, hor)
s2 = cv2.filter2D(Image, -1, ver)
EdgeDirection = np.zeros(Image.shape, np.float_)
Height, Width = s1.shape
if 'sum_sqrt' in FilterType:
EdgeAmplitude = np.sqrt(np.power(s1, 2) + np.power(s2, 2)) / 4
# EdgeDirection = np.arctan2(-s2, -s1)
elif 'sum_abs' in FilterType:
EdgeAmplitude = np.add(np.abs(s1), np.abs(s2)) / 4
EdgeAmplitudeMax = np.max(EdgeAmplitude)
EdgeAmplitudeMin = np.min(EdgeAmplitude)
EdgeAmplitudeNor = (EdgeAmplitude - EdgeAmplitudeMin) / (EdgeAmplitudeMax - EdgeAmplitudeMin) * 90
for y in range(Height):
for x in range(Width):
if s2[y, x] == 0 and s1[y, x] == 0:
EdgeDirection[y, x] = 255
continue
if s2[y, x] == 0 and s1[y, x] > 0:
EdgeDirection[y, x] = 0
continue
elif s2[y, x] < 0 and s1[y, x] > 0:
# EdgeDirection[y, x] = random.uniform(1, 89) 右下到左上
EdgeDirection[y, x] = abs(EdgeAmplitudeNor[y, x])
continue
elif s2[y, x] < 0 and s1[y, x] == 0:
EdgeDirection[y, x] = 90
continue
elif s2[y, x] < 0 and s1[y, x] < 0:
# EdgeDirection[y, x] = random.uniform(91, 179) 右上到左下
EdgeDirection[y, x] = 90 + abs(EdgeAmplitudeNor[y, x])
continue
elif s2[y, x] == 0 and s1[y, x] < 0:
EdgeDirection[y, x] = 180
continue
elif s2[y, x] > 0 and s1[y, x] < 0:
# EdgeDirection[y, x] = random.uniform(1, 45) 左上到右下
EdgeDirection[y, x] = 180 + abs(EdgeAmplitudeNor[y, x])
continue
elif s2[y, x] > 0 and s1[y, x] == 0:
EdgeDirection[y, x] = 270
continue
elif s2[y, x] > 0 and s1[y, x] > 0:
# EdgeDirection[y, x] = random.uniform(1, 45) 左下到右上
EdgeDirection[y, x] = 270 + abs(EdgeAmplitudeNor[y, x])
continue
return EdgeAmplitude.astype(np.uint8), EdgeDirection.astype(np.uint8)
我找到了一张随机图片进行测试,计算出的幅度值与Halcon软件完全相同,但是在角度图像中,我不知道如何在0到90、90到180之间分配这些灰度值。 ..
帮助...