zoukankan      html  css  js  c++  java
  • opencv再学习之路(八)---轮廓检测

    1.  例程

     1 //  轮廓寻找
     2   
     3 #include "stdafx.h"  
     4 #include <opencv2corecore.hpp>
     5 #include <opencv2imgprocimgproc.hpp>
     6 #include <opencv2highguihighgui.hpp>
     7 #include <iostream>
     8 #include <map>
     9 #include <string>
    10 #include<stdio.h>
    11 
    12 using namespace std;
    13 using namespace cv;
    14 
    15 
    16 void main()
    17 {
    18 
    19     Mat image = imread("03.jpg");
    20 
    21     Mat gray;
    22     cvtColor( image, gray, CV_RGB2GRAY);
    23 
    24     Mat binary;
    25     threshold( gray, binary, 150, 255, CV_THRESH_BINARY_INV);
    26 
    27     vector<vector<Point>> contours;
    28     Mat binary_copy;
    29     binary.copyTo(binary_copy);
    30     findContours( binary_copy, contours, CV_RETR_EXTERNAL, CV_CHAIN_APPROX_NONE);      //  CV_RETR_EXTERNAL 获取外轮廓 CV_CHAIN_APPROX_NONE 获取每个轮廓的像素
    31 
    32     // 遍历每一个轮廓,把多余的轮廓去掉
    33     vector<vector<Point>>::iterator it = contours.begin();
    34     while (it != contours.end())
    35     {
    36         if (it->size() < 500)
    37         {
    38             it = contours.erase(it);
    39         }
    40         else
    41             it++;
    42     }
    43 
    44     // 重新绘制轮廓
    45     Mat dst(image.size(), CV_8U, Scalar(0));
    46     drawContours( dst, contours, -1, Scalar(255), CV_FILLED);
    47     
    48     // 显示结果(原图和结果图显示在一起)
    49     const int width = image.cols;
    50     const int height = image.rows;
    51     Mat show_image(Size(width * 3,height), CV_8UC3);
    52     // 将image拷贝到指定位置上
    53     image.copyTo(show_image(Rect( 0, 0, width, height)));
    54     // 将binary,dst 转换为三通道,使得 dst 和 show_image 通道数一致
    55     cvtColor(binary, binary, CV_GRAY2BGR);
    56     cvtColor(dst, dst, CV_GRAY2BGR);
    57 
    58     // binary 和 dst拷贝到指定位置上
    59     binary.copyTo(show_image(Rect(width, 0, width,height)));
    60     dst.copyTo(show_image(Rect(width * 2, 0, width,height)));
    61 
    62     // 显示
    63     imshow("show", show_image);
    64     drawContours( image, contours, -1, Scalar(0,255,0), CV_FILLED);
    65     imshow("效果", image);
    66 
    67     waitKey(0);
    68 }

    2.函数解释

      void findContours( InputOutputArray image, OutputArrayOfArrays contours,  OutputArray hierarchy ,  int mode, int method, Point offset=Point());

      image    二值单通道图像

      contours           检测的轮廓数组,每一个轮廓用一个 Point 类型的 vector 表示

      hierarchy          轮廓个数相同,每一个轮廓 contours[i] 对应 4 个hierarchy[ i ][ 0 ] ~ hierarchy[ i ][ 3 ],分别表示后一个轮廓、前一个轮廓、父轮廓、内嵌轮廓的索引编号,如果没有对应项,该值设置为负数

      mode    表示轮廓的检索模式    

             CV_RETR_EXTERNAL 表示只检测外轮廓

             CV_RETR_LIST 检测的轮廓不建立等级关系

             CV_RETR_CCOMP建立两个等级的轮廓,上面的一层为边界信息,如果内孔内还有一个连通物体,这个物体的边界也在顶层

             CV_RETR_TREE 建立一个等级树结构的轮廓

      method    轮廓的近似方法

             CV_CHAIN_APPROX_NONE 存储所有的轮廓点,相邻的两个点的像素位置差不超过 1,即max(abs( x1 - x2)), abs(y2 - y1) == 1

             CV_CHAIN_APPROX_SIMPLE 压缩水平方向,垂直方向,对角线方向的元素,只保留该方向的终点坐标,例如: 一个矩形轮廓只需4个点来保存轮廓信息

             CV_CHAIN_APPROX_TC89_L1, CV_CHAIN_APPROX_TC89_KCOS 使用 teh-chinl 近似算法

      void drawContours( InputOutputArray image, InputArrayOfArrays contours,  int contourIdx, const Scalar& color,  int thickness=1, int lineType=8,  InputArray hierarchy=noArray(),  int maxLevel=INT_MAX, Point offset=Point() );

      image    目标图像,将轮廓绘制在此图像上

      contours      轮廓组,对应 findContours 里的 contours

      contourldx   指明第几个轮廓,如果是负数,则画出所有的轮廓

      color     轮廓颜色

      thickness   轮廓的线宽

      lineType    如果是负数或者使用 CV_FILLED 表示填充轮廓内部

      hierarchy     轮廓结构

      

      

  • 相关阅读:
    统计学(第六版)14单元——学习总结
    统计学(第六版)13单元——学习总结(时间序列分析总结)
    统计学(第六版)11到12单元——学习总结
    Kubernetes: 微内核的分布式操作系统
    彻底搞懂JavaScript之原型
    手把手带你玩转k8s-一键部署vue项目
    新一代缓存Caffeine,速度确实比Guava的Cache快
    理解 Es6 中的 Symbol 类型
    一天一大 leet(用两个栈实现队列)难度:简单 DAY-30
    (Java 源码阅读) 春眠不觉晓,HashMap知多少
  • 原文地址:https://www.cnblogs.com/zhp218/p/8646113.html
Copyright © 2011-2022 走看看