OpenCV 学习笔记

OpenCV 笔记(20):霍夫圆检测

2024-02-03  本文已影响0人  fengzhizi715

1. 霍夫圆变换

霍夫圆变换(Hough Circle Transform)是一种数字图像处理中的特征提取技术,用于在图像中检测圆形。它将二维图像空间中一个圆转换为该圆半径、圆心横纵坐标所确定的三维参数空间中一个点的过程。因此,圆周上任意三点所确定的圆,经霍夫变换后在三维参数空间应对应一点。

霍夫圆变换的优点:

霍夫圆变换的缺点:

2. 霍夫圆检测的原理

2.1 标准霍夫圆变换

圆的一般方程为: (𝑥−𝑎)^2+(𝑦−𝑏)^2=𝑟^2,其中 (a、b) 为圆心坐标,r 是圆的半径。

把图像空间转换成参数空间,这里将 x-y 平面转化成 a-b-r 参数空间,则在图像空间中的一个过 x、y 点的圆,对应参数空间中高度变化的三维锥面。

图像空间映射到霍夫空间.png

过图像空间上同一个圆的点,对应的参数空间中的三维锥面,在 r 平面必然相交于一点 (a, b, r) ,这样通过这一点就可以得到一个圆的参数。

图像空间上同一点的圆对应霍夫空间的三维锥面.png

标准霍夫圆变换的基本思想:对于图像中的每个边缘点,我们考虑所有可能通过该点的圆形。对于每个这样的圆形,我们将其参数 (a, b, r) 对应的累加器加 1。最终,累加器中值最大的点所对应的参数即为图像中存在的圆形参数。

2.2 霍夫梯度法

在 OpenCV 中使用了霍夫梯度法实现圆检测。霍夫梯度法是一种改进的霍夫圆变换算法,用于提高圆检测的效率和鲁棒性。

霍夫梯度法的基本原理:

使用梯度方向.png

霍夫梯度法包含以下步骤:

霍夫梯度法与霍夫圆检测的主要区别在于:

因此,霍夫梯度法相比于标准霍夫圆变换具有以下优点:

霍夫梯度法也存在以下的一些缺点:

3. 示例

OpenCV 提供了 cv::HoughCircles 函数用于检测图像中圆形的函数。

下面的例子,使用霍夫梯度法检测图中的硬币。

#include "opencv2/imgproc.hpp"
#include "opencv2/highgui.hpp"

using namespace std;
using namespace cv;

int main(int argc, char **argv) {
    Mat src = imread(".../coins.jpg");
    imshow("src", src);

    Mat gray;
    cvtColor(src, gray, cv::COLOR_BGR2GRAY); // 灰度化

    Mat gauss;
    GaussianBlur(gray, gauss, Size(15, 15),0); //降噪

    Mat thresh;
    threshold(gauss, thresh,0,255,THRESH_BINARY | THRESH_OTSU );
    imshow("thresh", thresh);

    vector<Vec3f> circles;
    cv::HoughCircles(thresh, circles, HOUGH_GRADIENT, 1, 50, 100,15,5,100);

    for (auto i = 0; i < circles.size(); i++)
    {
        Point center(cvRound(circles[i][0]), cvRound(circles[i][1]));
        int radius = cvRound(circles[i][2]);
        circle(src, center, 3, Scalar(0, 0, 255), -1, 8);
        circle(src, center, radius, Scalar(0, 0, 255), 3, 8);
    }
    imshow("result", src);

    waitKey(0);
    return 0;
}
霍夫圆检测的效果.png

下面详细介绍一下 HoughCircles 函数:

void HoughCircles( InputArray image, OutputArray circles,
                               int method, double dp, double minDist,
                               double param1 = 100, double param2 = 100,
                               int minRadius = 0, int maxRadius = 0 );

第一个参数 image: 输入图像,是 8 位单通道灰度图像。
第二个参数 circles: 输出圆形信息的容器,是一个 std::vector<Vec3f> 类型的数组,其中每个元素包含三个浮点数,分别代表圆心的 x 坐标、y 坐标和半径。
第三个参数 method: 圆形检测方法,目前支持 HOUGH_GRADIENTHOUGH_GRADIENT_ALT
第四个参数 dp: 累加器图像的分辨率与输入图像分辨率的比值倒数,默认为 1。
第五个参数 minDist: 检测到的圆心之间的最小距离,可以避免检测到重叠的圆形。
第六个参数 param1: HOUGH_GRADIENT 中的第一个参数,用于 Canny 边缘检测算子的高阈值,默认为 100。
第七个参数 param2: HOUGH_GRADIENT 中的第二个参数,用于在检测阶段对圆心累加器的阈值,默认为 100。
第八个参数 minRadius: 圆形的最小半径,默认为 0。
第九个参数 maxRadius: 圆形的最大半径,默认为 0。

4. 总结

霍夫圆检测是一种用于图像处理中圆形检测的经典方法,具有广泛的应用场景、良好的鲁棒性和准确性、灵活性和可扩展性、高效的计算性能以及易于理解和实现等优点,在许多领域发挥着重要作用。

上一篇 下一篇

猜你喜欢

热点阅读