使用霍夫变换检测圆形

8
我正在尝试使用霍夫变换检测圆形。
使用我的目前的代码,我可以检测到下面的圆形。
但是我想在检测到的圆形内部找到黑洞。然而改变霍夫圆方法的参数并没有帮助我。实际上它找到了不存在的圆。
我还尝试裁剪我找到的圆,并在这个新的部分上进行另一次霍夫变换,但也没有帮助我。
以下是我的代码:
#include <stdio.h>
#include <iostream>
#include "opencv2/core/core.hpp"
#include "opencv2/features2d/features2d.hpp"
#include "opencv2/highgui/highgui.hpp"
#include "opencv2/calib3d/calib3d.hpp"
#include "opencv2/nonfree/nonfree.hpp"
#include "opencv2/imgproc/imgproc.hpp"
#include "opencv2/opencv.hpp"  // needs imgproc, imgcodecs & highgui
using namespace cv;
using namespace std;

int main(int argc, char** argv)
{
    Mat src, circleroi;

    /// Read the image
    src = imread( "/Users/Rodrane/Documents/XCODE/test/mkedenemeleri/alev/delikli/gainfull.jpg", 2 );


    /// Convert it to gray
//    cvtColor( src, src_gray, CV_BGR2GRAY );
       /// Reduce the noise so we avoid false circle detection
   GaussianBlur( src, src, Size(3, 3), 2, 2 );
   // adaptiveThreshold(src,src,255,CV_ADAPTIVE_THRESH_MEAN_C,CV_THRESH_BINARY,9,14);
    vector<Vec3f> circles,circlessmall;
 //   Canny( src, src, 50  , 70, 3 );
       /// Apply the Hough Transform to find the circles
    HoughCircles( src, circles, CV_HOUGH_GRADIENT, 1, src.rows/8, 200, 100, 0, 0 );

    /// Draw the circles detected
    for( size_t i = 0; i < circles.size(); i++ )
    {
        Point center(cvRound(circles[i][0]), cvRound(circles[i][4]));
        int radius = cvRound(circles[i][5]);
        // circle center
     circle( src, center, 3, Scalar(0,255,0), -1, 8, 0 );
       //  circle outline
      circle( src, center, radius, Scalar(0,255,0), 3, 8, 0 );

         circleroi = src(Rect(center.x - radius, // ROI x-offset, left coordinate
                                        center.y - radius, // ROI y-offset, top coordinate
                                        2*radius,          // ROI width
                                        2*radius));



  //      imshow( "Hough Circle Transform Demo", circleroi );


}

  resize(src, src, Size(src.cols/2, src.rows/2));
//   threshold( circleroi, circleroi, 50, 255,CV_THRESH_BINARY );

  //  cout<<circleroi<<endl;
    imshow("asd",src);

   //    imwrite("/Users/Rodrane/Documents/XCODE/test/mkedenemeleri/alev/cikti/deliksiz.jpg",circleroi);


    waitKey(0);
    return 0;
}
更新: 由于hough在内部使用canny,我手动使用canny来查看是否可以找到圆。

这里是canny的结果: Canny(src,src,100,200,3); enter image description here

谢谢


你尝试过不进行阈值处理吗?HoughCircles 内部使用 Canny... - Micka
图像上没有阈值,只有高斯模糊用于照明,但我也已经禁用了它。 - Anar Bayramov
请您发布带有孔洞但没有黑色圆圈的图片,谢谢。我在前两张图片中看不到任何黑洞。 - kkuilla
你想要检测第一张图片中心的大黑洞,还是想要检测第三张图片中的小黑洞?我只能看到第一张图片中心的大黑洞。 - kkuilla
抱歉,我的手机上看起来好像没有注释中的阈值...你试过不使用模糊/边缘检测/阈值来进行灰度处理吗? - Micka
显示剩余5条评论
1个回答

1
您正在设置其中一个HoughCircles参数minDist = src.rows/8,这是相当大的。docs解释如下:

minDist - 检测到的圆心之间的最小距离。如果参数太小,则可能会错误地检测到多个相邻圆形以及一个真实的圆形。如果太大,则可能会漏掉一些圆形。

由于它们的中心非常接近(在src.rows/8内),只是大小不同,因此该方法无法同时返回它找到的圆和您想要的圆。如果将maxRadius设置为约30以排除较大的圆,是否可以获得所需的较小圆?

嗨,我已经尝试了HoughCircles(src,circles,CV_HOUGH_GRADIENT,1,src.rows / 16(32,64),200,100,0,30);但是没有找到任何圆。 - Anar Bayramov
嗯,也许 param2 太大了。值得尝试更小的值。如果这样还不行,你可以显示从 Canny(src, edges, 100, 200) 输出的 edges,确保它首先找到了内圆的边缘。 - Chris Culter
嗨,让我用Canny算法的结果更新一下我的问题。 - Anar Bayramov

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接