演示代码:
#include <opencv2/opencv.hpp> #include <iostream> #include <math.h> using namespace cv; using namespace std; int main(int argc, char** argv) { Mat src, dst; src = imread("e:/circle.png"); //中值滤波 Mat mOut; medianBlur(src, mOut, 3); cvtColor(mOut, mOut, CV_BGR2GRAY); //找霍夫圆 vector<Vec3f> cir; HoughCircles(mOut, cir, CV_HOUGH_GRADIENT, 1, 10, 100, 30, 5, 50); src.copyTo(dst); for (size_t i = 0; i < cir.size(); i++) { Vec3f cc = cir[i]; circle(dst, Point(cc[0], cc[1]), cc[2], Scalar(0, 0, 255), 2, LINE_AA); circle(dst, Point(cc[0], cc[1]),2, Scalar(255, 0, 0), 2, LINE_AA); } imshow("findcircle", dst); waitKey(0); return 0; }
代码说明:
霍夫圆检测原理
霍夫圆变换原理
从平面坐标到极坐标转换三个参数
假设平面坐标的任意一个圆上的点,转换到极坐标中:
处有最大值,霍夫变换正是利用这个原理实现圆的检测。
相关API cv::HoughCircles
因为霍夫圆检测对噪声比较敏感,所以首先要对图像做中值滤波。
基于效率考虑,Opencv中实现的霍夫变换圆检测是基于图像梯度的实现,分为两步:
1. 检测边缘,发现可能的圆心
2. 基于第一步的基础上从候选圆心开始计算最佳半径大小
HoughCircles参数说明
HoughCircles( InputArray image, // 输入图像 ,必须是8位的单通道灰度图像 OutputArray circles, // 输出结果,发现的圆信息 Int method, // 方法 - HOUGH_GRADIENT Double dp, // dp = 1; Double mindist, // 10 最短距离-可以分辨是两个圆的,否则认为是同心圆- src_gray.rows/8 Double param1, // canny edge detection low threshold Double param2, // 中心点累加器阈值 – 候选圆心 Int minradius, // 最小半径 Int maxradius//最大半径 )
---------------------
作者:hackpig
来源:www.skcircle.com
版权声明:本文章代码及资料部分或全部来自贾志刚老师的视频,勇哥只是在个人理解的基础上做学习笔记,转载请附上博文链接!
本文出自勇哥的网站《少有人走的路》wwww.skcircle.com,转载请注明出处!讨论可扫码加群: