opencv 查找连通区域 最大面积实例


Posted in Python onJune 04, 2020

今天在弄一个查找连通的最大面积的问题。

要把图像弄成黑底,白字,这样才可以正确找到。

然后调用下边的方法:

RETR_CCOMP:提取所有轮廓,并将轮廓组织成双层结构(two-level hierarchy),顶层为连通域的外围边界,次层位内层边界

#include <opencv2/imgproc.hpp>
#include <opencv2/highgui.hpp>
 
using namespace cv;
using namespace std;
 
int main( int argc, char** argv )
{
  Mat src = imread( argv[1] );
 
  int largest_area=0;
  int largest_contour_index=0;
  Rect bounding_rect;
 
  Mat thr;
  cvtColor( src, thr, COLOR_BGR2GRAY ); //Convert to gray
  threshold( thr, thr, 125, 255, THRESH_BINARY ); //Threshold the gray
  bitwise_not(thr,thr); //这里先变反转颜色
 
  vector<vector<Point> > contours; // Vector for storing contours
 
  findContours( thr, contours, RETR_CCOMP, CHAIN_APPROX_SIMPLE ); // Find the contours in the image
 
  for( size_t i = 0; i< contours.size(); i++ ) // iterate through each contour.
  {
    double area = contourArea( contours[i] ); // Find the area of contour
 
    if( area > largest_area )
    {
      largest_area = area;
      largest_contour_index = i;        //Store the index of largest contour
      bounding_rect = boundingRect( contours[i] ); // Find the bounding rectangle for biggest contour
    }
  }
 
  drawContours( src, contours,largest_contour_index, Scalar( 0, 255, 0 ), 2 ); // Draw the largest contour using previously stored index.
 
  imshow( "result", src );
  waitKey();
  return 0;
}

方法二: connectedComponentsWithStats

std::pair< int , int > MaxAreaFromSource(Mat srcImage, Mat &dstImage, int index)
{
  /*
  vector<vector<cv::Point> > contours; // Vector for storing contours
  
  int largest_area=0;
  size_t largest_contour_index=0;
  Rect bounding_rect;
  
  findContours( srcImage, contours, RETR_CCOMP, CHAIN_APPROX_SIMPLE ); // Find the contours in the image
  
  for( size_t i = 0; i< contours.size(); i++ ) // iterate through each contour.
  {
    double area = contourArea( contours[i] ); // Find the area of contour
    
    if( area > largest_area )
    {
      largest_area = area;
      largest_contour_index = i;        //Store the index of largest contour
      bounding_rect = boundingRect( contours[i] ); // Find the bounding rectangle for biggest contour
    }
  }
  
  Mat dst;
  cvtColor(srcImage, dst, CV_GRAY2RGB);
  drawContours( dst, contours,largest_contour_index, Scalar( 0, 255, 0 ), 2 ); // Draw the largest contour using previously stored index.
  imshow( "result", dst );
  waitKey();
  
  printf("%%%%%%%%%%%max area:%d\n", largest_area);
  return make_pair( largest_area, index);
  */
  
  cv::Mat img_bool, labels, stats, centroids, img_color, img_gray;
  
  //连通域计算
  int nccomps = cv::connectedComponentsWithStats (
                          srcImage, //二值图像
                          labels,   //和原图一样大的标记图
                          stats, //nccomps×5的矩阵 表示每个连通区域的外接矩形和面积(pixel)
                          centroids //nccomps×2的矩阵 表示每个连通区域的质心
                          );
  //cv::imshow("labels", labels);
  //cv::waitKey();
  
  vector<cv::Vec3b> colors(nccomps);
  colors[0] = cv::Vec3b(0,0,0); // background pixels remain black.
  
   printf( "index:%d==================\n",index );
  
  vector< int >vec_width,vec_area,vec_height;
  
  for(int label = 1; label < nccomps; ++label)
  {
    colors[label] = cv::Vec3b( (std::rand()&255), (std::rand()&255), (std::rand()&255) );
    std::cout << "Component "<< label << std::endl;
    std::cout << "CC_STAT_LEFT  = " << stats.at<int>(label,cv::CC_STAT_LEFT) << std::endl;
    std::cout << "CC_STAT_TOP  = " << stats.at<int>(label,cv::CC_STAT_TOP) << std::endl;
    std::cout << "CC_STAT_WIDTH = " << stats.at<int>(label,cv::CC_STAT_WIDTH) << std::endl;
    std::cout << "CC_STAT_HEIGHT = " << stats.at<int>(label,cv::CC_STAT_HEIGHT) << std::endl;
    std::cout << "CC_STAT_AREA  = " << stats.at<int>(label,cv::CC_STAT_AREA) << std::endl;
    std::cout << "CENTER  = (" << centroids.at<double>(label, 0) <<","<< centroids.at<double>(label, 1) << ")"<< std::endl << std::endl;
    
    int area = stats.at<int>(label,cv::CC_STAT_AREA);
    int left = stats.at<int>(label,cv::CC_STAT_LEFT);
    int top = stats.at<int>(label,cv::CC_STAT_TOP);
    int width = stats.at<int>(label,cv::CC_STAT_WIDTH);
    int height = stats.at<int>(label,cv::CC_STAT_HEIGHT);
    
    vec_area.push_back(area);
    vec_width.push_back(width);
    vec_height.push_back(height);
  }
  
  vector<int>::iterator bigwidth = std::max_element(std::begin(vec_width), std::end(vec_width));
  vector<int>::iterator bigheight = std::max_element(std::begin(vec_height), std::end(vec_height));
  vector<int>::iterator bigarea = std::max_element(std::begin(vec_area), std::end(vec_area));
  
  //printf( "area:%d------------width:%d height:%d \n", *bigarea, *bigwidth, *bigheight );
  
  //按照label值,对不同的连通域进行着色
  img_color = cv::Mat::zeros(srcImage.size(), CV_8UC3);
  for( int y = 0; y < img_color.rows; y++ )
    for( int x = 0; x < img_color.cols; x++ )
    {
      int label = labels.at<int>(y, x);
      CV_Assert(0 <= label && label <= nccomps);
      img_color.at<cv::Vec3b>(y, x) = colors[label];
    }
  
  cv::imshow("color", img_color);
  cv::waitKey();
   
  return make_pair( *bigarea , index );
}

我先用这个函数实现了一下,效果正确,还是opencv demo 是正确的,网上找了个例子,害死我了。

说明一下:方法一 比 第二种方法 运行速度快很多哦! 这一点很重要。

以上这篇opencv 查找连通区域 最大面积实例就是小编分享给大家的全部内容了,希望能给大家一个参考,也希望大家多多支持三水点靠木。

Python 相关文章推荐
jupyter安装小结
Mar 13 Python
python 中random模块的常用方法总结
Jul 08 Python
使用Python搭建虚拟环境的配置方法
Feb 28 Python
Python查找文件中包含中文的行方法
Dec 19 Python
python批量爬取下载抖音视频
Jun 17 Python
利用python实现周期财务统计可视化
Aug 25 Python
django使用xadmin的全局配置详解
Nov 15 Python
python不相等的两个字符串的 if 条件判断为True详解
Mar 12 Python
浅谈TensorFlow之稀疏张量表示
Jun 30 Python
推荐值得学习的12款python-web开发框架
Aug 10 Python
python进度条显示-tqmd模块的实现示例
Aug 23 Python
Python基础之元类详解
Apr 29 Python
Python中的Cookie模块如何使用
Jun 04 #Python
Python爬虫获取页面所有URL链接过程详解
Jun 04 #Python
Python中的全局变量如何理解
Jun 04 #Python
使用OpenCV获取图片连通域数量,并用不同颜色标记函
Jun 04 #Python
Python urllib2运行过程原理解析
Jun 04 #Python
Python如何生成xml文件
Jun 04 #Python
基于python代码批量处理图片resize
Jun 04 #Python
You might like
PHP IN_ARRAY 函数使用注意事项
2010/07/24 PHP
让PHP COOKIE立即生效,不用刷新就可以使用
2011/03/09 PHP
php实现分页显示
2015/11/03 PHP
PHP汉字转换拼音的函数代码
2015/12/30 PHP
php生成二维码图片方法汇总
2016/12/17 PHP
Laravel 集成微信用户登录和绑定的实现
2019/12/27 PHP
thinkphp5.1 框架导入/导出excel文件操作示例
2020/05/25 PHP
jQuery阻止同类型事件小结
2013/04/19 Javascript
js判断浏览器是否支持html5
2014/08/17 Javascript
Javascript基础教程之argument 详解
2015/01/18 Javascript
js控制文本框输入的字符类型方法汇总
2015/06/19 Javascript
jquery+html5烂漫爱心表白动画代码分享
2015/08/24 Javascript
JavaScript学习小结(一)——JavaScript入门基础
2015/09/02 Javascript
CascadeView级联组件实现思路详解(分离思想和单链表)
2016/04/12 Javascript
利用原生js和jQuery实现单选框的勾选和取消操作的方法
2016/09/04 Javascript
Javascript创建类和对象详解
2017/05/31 Javascript
Angular4开发解决跨域问题详解
2017/08/28 Javascript
EasyUI的DataGrid绑定Json数据源的示例代码
2017/12/16 Javascript
jQuery使用动画队列自定义动画操作示例
2018/06/16 jQuery
关于React动态加载路由处理的相关问题
2019/01/07 Javascript
vue集成kindeditor富文本的实现示例代码
2019/06/07 Javascript
vue实现树形结构样式和功能的实例代码
2019/10/15 Javascript
jQuery 实现扁平式小清新导航
2020/07/07 jQuery
Element中Slider滑块的具体使用
2020/07/29 Javascript
浅谈function(函数)中的动态参数
2017/04/30 Python
简单实现python进度条脚本
2017/12/18 Python
浅谈Python使用Bottle来提供一个简单的web服务
2017/12/27 Python
python实现log日志的示例代码
2018/04/28 Python
Flask框架踩坑之ajax跨域请求实现
2019/02/22 Python
HTML5+CSS3网页加载进度条的实现,下载进度条的代码实例
2016/12/30 HTML / CSS
英国儿童图书网站:Scholastic
2017/03/26 全球购物
名人珠宝设计师:Melinda Maria Jewelry
2019/03/06 全球购物
计算机网络专业推荐信
2013/11/24 职场文书
我的中国梦演讲稿1000字
2014/08/19 职场文书
学习委员竞选稿
2015/11/20 职场文书
Go归并排序算法的实现方法
2022/04/06 Golang