【OpenCV】一种基于阈值的图片中的文字分割
来源:互联网 发布:淘宝起名字 编辑:程序博客网 时间:2024/05/16 14:05
在今年泰迪杯A题电商中图片的文字识别这道题中,我们先用了一种很笨的办法来分割字符。
首先对图片进行灰度化,然后二值化,这里的二值化要选择一个合适的阈值。然后我们进行轮廓的提取,计算轮廓最小矩形的面积,若面积过大,则认为这个是背景图片,若面积过小,则认为是噪点。这种方法有一个弊端,就是文字有大有小,大的文字也有可能会被当成背景,小的标点也可能会被当成噪点。
代码如下:
实现了读入一张图片,进行灰度化,二值化,分割字符,输出字符.jpg到指定位置,以及输出字符最小矩形的坐标。
const string imagename = "1.jpg"; //此处需要填写绝对地址,我测试时使用相对地址出错。 //读入图像 Mat img = imread(imagename); //如果读入图像失败 if (img.empty()) { return -1; } int Hmin = 0, Hmax = 156; int AreaMin = 15, AreaMax = 135; int Area = 200; //创建窗口 cv::namedWindow("thresh"); cv::createTrackbar("Hmin", "thresh", &Hmin, 255, NULL); cv::createTrackbar("Hmax", "thresh", &Hmax, 255, NULL); cv::createTrackbar("AreaMin", "thresh", &AreaMin, 200, NULL); cv::createTrackbar("AreaMax", "thresh", &AreaMax, 200, NULL); cv::createTrackbar("Area", "thresh", &Area, 4000, NULL); for (;;){ int _Hmin = Hmin, _Hmax = Hmax; int _AreaMin = AreaMin, _AreaMax = AreaMax; Mat HSV, thresh, GRAY,gray,src; //vector<Mat> channels; cvtColor(img, GRAY, CV_BGR2GRAY); //cvtColor(img, HSV, CV_BGR2HSV); //CV_BGR2GRAY转为灰度 CV_BGR2HSV转为HSV CV_BGR2YUV转为YUV CV_BGR2YCrCb转为YCrCb //split(HSV, channels); // channels[2]=0; inRange(GRAY, cv::Scalar(MIN(_Hmin, _Hmax), MIN(0, 255), MIN(0, 255)), cv::Scalar(MAX(_Hmin, _Hmax), MAX(0, 255), MAX(0, 255)), //scalar 中 (b,g,r,0) 即bgr 而非 rgb thresh);//color gray = GRAY; thresh = 255 - thresh; //cvShowImage("ThresholdImg", GRAY); dilate(thresh, thresh, NULL, cv::Point(-1, -1), 30); erode(thresh, thresh, NULL, cv::Point(-1, -1), 30); cv::imshow("thres", thresh); cv::waitKey(1); vector<cv::vector<cv::Point> > contours; vector<cv::Vec4i> hierarchy; // 找出图像中的最大轮廓 findContours(thresh, contours, hierarchy, CV_RETR_TREE, CV_CHAIN_APPROX_SIMPLE, cv::Point(0, 0)); // 定义一个 Rect 矢量来存放轮廓。因为轮廓的外形多数时候是不规则的。所以用一个矩形来代替 不规则的轮廓会在各种方面都方便很多。 //printf("轮廓个数:%d", contours.size()); cv::vector<cv::vector<cv::Point> > contours_poly(contours.size()); cv::vector<cv::Rect> boundRect(contours.size()); cv::vector<cv::Point2f>center(contours.size()); cv::vector<float>radius(contours.size()); int maxArea = 0; int index = 0; int minArea = 50; int ci = 0; for (unsigned int i = 0; i<contours.size(); i++) // 用一个 for 循环语句查看计算机找到的全部轮廓 { int area = contourArea(contours[i]);// 计算当前轮廓的包含面积 if (area> maxArea) // 找出包含面积最大的轮廓 { maxArea = area; index = i; } if (area<_AreaMax&&area>_AreaMin) { ci++; approxPolyDP(cv::Mat(contours[i]), contours_poly[i], 3, true); // approxPolyDP() 用来找出轮廓的近似多边形。用于简化轮廓的复杂度,加速计算过程。 boundRect[i] = cv::boundingRect(cv::Mat(contours_poly[i])); //BoundingRect() 是一个用来找出轮廓最小包围矩形函数。 //最小包围矩形的意思就是用 4 条边从 上下左右四个方向把轮廓紧紧夹在中间。这 4 条边构成的矩形就是最小包围矩形。 //drawContours(img, contours, i, CV_RGB(255, 255, 255), 1, 8, hierarchy, 0, cv::Point()); // 画出物体的轮廓 rectangle(GRAY, boundRect[i].tl(), boundRect[i].br(), CV_RGB(255, 0, 0), 2, 8, 0); // 画出物体的最小包围矩形 // 矩形的自然就是 boundRect() 算出的轮廓。 //printf("左上角x坐标:%d左上角y坐标:%d ", boundRect[i].tl().x, boundRect[i].tl().y); //printf("右下角x坐标:%d右下角y坐标:%d ", boundRect[i].br().x,boundRect[i].br().y); printf("PA%dPA %d %d %d %d\n",i,boundRect[i].tl().x, boundRect[i].br().y, boundRect[i].br().x, boundRect[i].tl().y); //printf("左下角x坐标:%d左下角y坐标:%d 右上角x坐标:%d右上角y坐标:%d ", boundRect[i].tl().x, boundRect[i].br().y, boundRect[i].br().x, boundRect[i].tl().y); Mat imgROI = img(Rect(boundRect[i].tl().x, boundRect[i].tl().y, std::abs(boundRect[i].br().x - boundRect[i].tl().x), std::abs(boundRect[i].br().y - boundRect[i].tl().y))); CString _file; _file.Format("./test/%d.jpg", i+1); std::string path = _file; imwrite(path, imgROI); } } //printf("字数:%d", ci); //imshow("HSV", HSV); imshow("GRAY", GRAY); //创建窗口 //显示图像 // namedWindow("SRC", 1); imshow("img", img); CString _file; _file.Format("gray.jpg"); std::string path = _file; imwrite(path, GRAY); // imshow("it", thresh); //等待按键,按键盘任意键返回 waitKey(0); }
0 0
- 【OpenCV】一种基于阈值的图片中的文字分割
- 基于opencv的阈值分割
- 12基于opencv的固定阈值分割_自适应阈值分割
- 图片中的字符分割提取(基于opencv)
- 阈值分割中全局阈值自动确定的一种方法
- 利用OpenCV实现图像的阈值分割
- opencv我的单通道阈值分割
- OpenCV--阈值分割-threshold()
- opencv中几种阈值分割
- 基于阈值法的图像分割技术
- 基于阈值法的图像分割技术
- 基于二维直方图的阈值分割
- 图像分割 1.基于阈值的算法
- 基于OpenCV和C++实现最大阈值分割算法
- 基于阈值图像分割
- OpenCV的otsu自适应阈值分割的算法在肤色检测中的应用
- otsu自适应阈值分割的算法描述和opencv实现,及其在肤色检测中的应用
- otsu自适应阈值分割的算法描述和opencv实现,及其在肤色检测中的应用
- 自定义Listview适配器的优化
- 我没有解决的迷之错误
- 数据结构栈的操作
- 同一个服务器上的不同项目要注意session的死锁问题
- Eclipse安装Swing插件
- 【OpenCV】一种基于阈值的图片中的文字分割
- 动态规划专题总结
- 使用ngrok暴露内网服务到公网
- SIP协议学习
- 未来发展的方向
- onethink后台上传图片,同一张图只能上传一次的问题
- CodeForces 246A. Buggy Sorting【思维】
- LevelDb
- 【步兵 c++】教科书般的A*寻路算法