opencv对象提取

对象提取,简而言之就是获取指定图像,去除其他图像.

解决思路

 二值处理 + 形态学处理(开运算+闭运算,轮廓发现) + 横纵比过滤计算 .
#include 
#include
#include 
#include
#include
#include
using namespace cv;
using namespace std;
Mat src,binary,dst;
int main()
{
	 src = imread("E:\\Users\\opencvCoder\\image\\yuan.png", IMREAD_GRAYSCALE);
	if (src.empty())
	{
		printf("could not load image...\n");
		return -1;
	}

	namedWindow("input image", WINDOW_AUTOSIZE);
	imshow("input image", src);

	//二值化图像
	threshold(src, binary, 0, 255, THRESH_BINARY | THRESH_OTSU);
	imshow("binary image", binary);

	//形态学操作
	Mat kernel = getStructuringElement(MORPH_RECT, Size(3, 3), Point(-1, -1));

	//闭操作,把中间的细小点联通起来
	morphologyEx(binary, dst, MORPH_CLOSE, kernel, Point(-1, -1));
	imshow("close image", dst);

	 kernel = getStructuringElement(MORPH_RECT, Size(3, 3), Point(-1, -1));
	 //开操作,去除多余的点
	morphologyEx(binary, dst, MORPH_OPEN, kernel, Point(-1, -1));
	imshow("open image", dst);

	/*---------------------获取对象轮廓-------------------------*/
	vector<vector<Point>>contours;
	vector<Vec4i>hireachy;
	findContours(dst, contours, hireachy, RETR_TREE, CHAIN_APPROX_SIMPLE, Point());

	Mat resultImage = Mat::zeros(src.size(), CV_8UC3);
	
	for (size_t t = 0; t < contours.size(); t++)
	{
		//面积过滤
		double area = contourArea(contours[t]);//获取每个轮廓围成的面积
		if (area < 100) continue;				//如果轮廓围成的面积小于100,则过滤
		//横纵比过滤
		Rect rect = boundingRect(contours[t]);//用最小的外接矩形把对象给包起来
		float ratio = float(rect.width) / float(rect.height);
		if (ratio < 1.1 && ratio>0.9)//因为检测提取的对象是圆,所以横纵比可以设定为在0.9-1.2之间
		{
			drawContours(resultImage, contours, t, Scalar(0, 0, 255), 2, 8, Mat(), 0, Point());
			printf("circle area:%f\n", area);//面积
			printf("circle length:%f\n", arcLength(contours[t],true));//周长

		}


	}
	imshow("result image", resultImage);

	//detect circle
	/*----------------获取圆点坐标方法1----------------------*/

	//int x = rect.x + rect.width / 2;//rect.x是矩形左上角的横坐标
	//int y = rect.y + rect.height / 2;//rect.y是矩形左上角的纵坐标
	//cc = Point(x, y);
	Scalar color = Scalar(rng.uniform(0, 255), rng.uniform(0, 255), rng.uniform(0, 255));
	//circle(result_img, cc, 2, Scalar(0, 0, 255), 2, 8, 0);

	/*----------------获取圆点坐标方法2----------------------*/
	vector<Vec3f>myCircles;
	Mat gray_result;
	cvtColor(resultImage, gray_result, COLOR_BGR2GRAY);
	HoughCircles(gray_result, myCircles, HOUGH_GRADIENT, 1, 10,100,30,10,gray_result.rows/4);

	Mat circleImage = src.clone();
	cvtColor(circleImage, circleImage, COLOR_GRAY2BGR);
	for (int i = 0; i < myCircles.size(); i++)
	{
		Vec3f circleInfo = myCircles[i];
		circle(circleImage, Point(circleInfo[0], circleInfo[1]),circleInfo[2], Scalar(0, 0, 255), 2, 8, 0);
	}

	imshow("Final Result", circleImage);
	waitKey(0);
	return 0;
}

opencv对象提取_第1张图片

你可能感兴趣的:(图像处理,C/C++,opencv,计算机视觉,c++)