OpenCV canny边缘检测在理想方块上无法正常工作

Adi*_*ade 5 python opencv edge-detection canny-operator

我正在使用15*15像素的二进制方形图像.

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
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 1 1 1 1 1 1 1 1 1 1 0 0
0 0 0 1 1 1 1 1 1 1 1 1 0 0
0 0 0 1 1 1 1 1 1 1 1 1 0 0
0 0 0 1 1 1 1 1 1 1 1 1 1 0 0
0 0 0 1 1 1 1 1 1 1 1 1 0 0
0 0 0 1 1 1 1 1 1 1 1 1 1 0
0 0 0 1 1 1 1 1 1 1 1 1 1 0 0
0 0 0 1 1 1 1 1 1 1 1 1 0 0
0 0 0 1 1 1 1 1 1 1 1 1 0 0
0 0 0 1 1 1 1 1 1 1 1 1 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 0 0 0 0 0

我正在应用openCV(2.7版)提供的canny边缘检测来进行对象大小测量.我的预期输出应该是,

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
0 0 0 0 0 0 0 0 0 0 0 0 0 0 0
0 0 0 1 1 1 1 1 1 1 1 1 1 0 0
0 0 0 1 0 0 0 0 0 0 0 0 1 0 0
0 0 0 1 0 0 0 0 0 0 0 0 1 0 0
0 0 0 1 0 0 0 0 0 0 0 0 1 0 0
0 0 0 1 0 0 0 0 0 0 0 0 1 0 0
0 0 0 1 0 0 0 0 0 0 0 0 1 0 0
0 0 0 1 0 0 0 0 0 0 0 0 1 0 0
0 0 0 1 0 0 0 0 0 0 0 0 1 0 0
0 0 0 1 0 0 0 0 0 0 0 0 1 0 0
0 0 0 1 1 1 1 1 1 1 1 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 0 0 0 0 0

但是两个边缘(顶部和左边缘)总是偏移一个像素.canny边缘检测的输出为,
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 0 0
0 0 1 1 1 1 1 1 1 0 0 0
0 0 0 1 0 0 0 0 0 0 0 0 1 0 0
0 0 1 0 0 0 0 0 0 0 0 0 1 0 0
0 0 1 0 0 0 0 0 0 0 0 0 1 0 0
0 0 1 0 0 0 0 0 0 0 0 0 1 0 0
0 0 1 0 0 0 0 0 0 0 0 0 1 0 0
0 0 1 0 0 0 0 0 0 0 0 0 1 0 0
0 0 1 0 0 0 0 0 0 0 0 0 1 0 0
0 0 1 0 0 0 0 0 0 0 0 0 1 0 0
0 0 1 0 0 0 0 0 0 0 0 0 1 0 0
0 0 0 1 1 1 1 1 1 1 1 1 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 0 0 0 0 0

为什么这个像素发生变化?
有什么办法可以避免这种情况.(我不能在输出后手动调整像素移位,因为我必须对不规则形状使用边缘检测)无论奇数/偶数像素如何,都会发生相同的移位.

Jer*_*uke 5

乍一看,当我遇到这个问题时,我感到非常惊讶.而且我不相信Canny边缘检测会如此欺骗.所以我采用了类似的图像并将Canny边缘应用于它.令我惊讶的是,我遇到了你面临的同样问题.为什么会这样?

在深入研究文档后,我遇到了很多在幕后发生的操作.

文档声称高斯滤波是为了降低噪声.嗯,这是真的.但这也模糊了图像中存在的现有边缘.因此,当您模糊完美的正方形/矩形时,它往往会有弯曲的角落.

在高斯滤波之后,下一步是找到边缘梯度.如上所述,到目前为止,由于模糊(高斯滤波),正方形/矩形的完美边缘消失了.剩下的是圆形/弯曲边缘.在圆形/弯曲边缘上找到渐变的强度永远不会产生完美的方形/矩形边缘.我可能错了,但我猜这是为什么我们在执行Canny边缘检测时没有获得完美边缘的主要原因.

如果你想要一个完美的边缘,我的建议是尝试找到轮廓(如Micka所建议的)并绘制一个边界矩形.