当前位置:文档之家› 图像轮廓提取

图像轮廓提取

OpenCV笔记9:提取并显示图像轮廓
01#include <cv.h>
02#include <cxcore.h>
03#include <highgui.h>
04#include <iostream.h>
05void main()
06{
07int i=0;
08int mode=CV_RETR_CCOMP; //提取轮廓的模式
09int contoursNum=0; //提取轮廓的数目
10CvScalar externalColor;
11CvScalar holeColor;
12CvMemStorage*storage=cvCreateMemStorage(0); //提取轮廓需要的储存容量0为默认64KB
13CvSeq*pcontour=0; //提取轮廓的序列指针
14IplImage*pImg=NULL;
15IplImage*pContourImg=NULL;
16IplImage*src=cvLoadImage("pic3.png",-1);
17pImg=cvCreateImage(cvGetSize(src),src->depth,1);
18pContourImg=cvCreateImage(cvGetSize(pImg),IPL_DEPTH_8U,3);
19cvCvtColor(src,pImg,CV_RGB2GRAY); //将图像转换为灰度
20cvNamedWindow("src",CV_WINDOW_AUTOSIZE);
21cvNamedWindow("pcontour",CV_WINDOW_AUTOSIZE);
22cvShowImage("src",src);
23cvThreshold(pImg,pImg,180,255,CV_THRESH_BINARY); //二值化
24//--------------查找轮廓----------------
25mode=CV_RETR_LIST;
26
contoursNum=cvFindContours(pImg,storage,&pcontour,sizeof(CvContour),mode,CV_CHAIN_APPRO X_NONE);
27cout<<contoursNum<<" "<<endl;
28//--------------画轮廓----------------
29for (;pcontour!=0;pcontour=pcontour->h_next)
30{
31holeColor=CV_RGB(rand()&255,rand()&255,rand()&255);
32externalColor=CV_RGB(rand()&255,rand()&255,rand()&255);
33cvDrawContours(pContourImg,pcontour,externalColor,holeColor,1,2,8);
34}
35cvShowImage("pcontour",pContourImg);
36cvWaitKey(0);
37cvReleaseImage(&src);
38cvReleaseImage(&pImg);
39cvReleaseImage(&pContourImg);
40}
==========================================================
==========================================================
cvFindContours原型:
int cvFindContours( CvArr* image, CvMemStorage* storage, CvSeq** first_contour, int
header_size=sizeof(CvContour), int mode=CV_RETR_LIST, int method=CV_CHAIN_APPROX_SIMPLE, CvPoint ōffset=cvPoint(0,0) );
image 输入的8-比特、单通道图像。

为了从灰度图像中得到这样的二值图像,可以使用cvThreshold、cvAdaptiveThreshold 或cvCanny,改变输入图像内容。

storage 得到的轮廓的存储容器first_contour 输出参数:包含第一个输出轮廓的指针header_size 如果method=CV_CHAIN_CODE,则序列头的大小>=sizeof(CvChain),否则>=sizeof(CvContour)。

mode 提取模式:
CV_RETR_EXTERNAL - 只提取最外层的轮廓;
CV_RETR_LIST - 提取所有轮廓,并且放置在list 中;
CV_RETR_CCOMP - 提取所有轮廓,并且将其组织为两层的hierarchy: 顶层为连通域的外围边界,次层为洞的内层边界;
CV_RETR_TREE - 提取所有轮廓,并且重构嵌套轮廓的全部hierarchy;
method 逼近方法:
(对所有节点, 不包括使用内部逼近的CV_RETR_RUNS)
CV_CHAIN_CODE - Freeman 链码的输出轮廓. 其它方法输出多边形(定点序列);
CV_CHAIN_APPROX_NONE - 将所有点由链码形式翻译为点序列形式;
CV_CHAIN_APPROX_SIMPLE - 压缩水平、垂直和对角分割,即函数只保留末端的象素点;
CV_CHAIN_APPROX_TC89_L1, CV_CHAIN_APPROX_TC89_KCOS - 应用Teh-Chin 链逼近算法;CV_LINK_RUNS - 通过连接为1 的水平碎片使用完全不同的轮廓提取算法;
offset 每一个轮廓点的偏移量,当轮廓是从图像ROI 中提取出来的时候,使用偏移量有用,因为可以从整个图像上下文来对轮廓做分析。

函数cvFindContours 从二值图像中提取轮廓,并且返回提取轮廓的数目。

指针first_contour 的内容由函数填写。

它包含第一个最外层轮廓的指针,如果指针为NULL,则没有检测到轮廓(比如图像是全黑的)。

其它轮廓可以从first_contour 利用h_next 和v_next 链接访问到。

在cvDrawContours 的样例显示如何使用轮廓来进行连通域的检测。

相关主题