请问WiFi万能钥匙(推荐)发送扣费短信是干什么的?注册账号吗?注册的账号在哪里呢?

您所在的位置: &
OpenCV成长之路:直线、轮廓的提取与描述
OpenCV成长之路:直线、轮廓的提取与描述
基于内容的图像分析的重点是提取出图像中具有代表性的特征,而线条、轮廓、块往往是最能体现特征的几个元素,这篇文章就针对于这几个重要的图像特征,研究它们在OpenCV中的用法,以及做一些简单的基础应用。
本文是51CTO博客作者Ronny的文章,。
基于内容的图像分析的重点是提取出图像中具有代表性的特征,而线条、轮廓、块往往是最能体现特征的几个元素,这篇文章就针对于这几个重要的图像特征,研究它们在OpenCV中的用法,以及做一些简单的基础应用。
一、Canny检测轮廓
在 上一篇文章中有提到sobel边缘检测,并重写了soble的C++代码让其与matlab中算法效果一致,而soble边缘检测是基于单一阈值的,我们 不能兼顾到低阈值的丰富边缘和高阈值时的边缘缺失这两个问题。而canny算子则很好的弥补了这一不足,从目前看来,canny边缘检测在做图像轮廓提取 方面是最优秀的边缘检测算法。
canny边缘检测采用双阈值值法,高阈值用来检测图像中重要的、显著的线条、轮廓等,而低阈值用来保证不丢失细节部分,低阈值检测出来的边缘更丰富,但是很多边缘并不是我们关心的。最后采用一种查找算法,将低阈值中与高阈值的边缘有重叠的线条保留,其他的线条都删除。
本篇文章中不对canny的算法原理作进一步说明,稍后会在图像处理算法相关的文章中详细介绍。
下面我们用OpenCV中的Canny函数来检测图像边缘
int&main()&{&&&&&Mat&I=imread(&../cat.png&);&&&&&cvtColor(I,I,CV_BGR2GRAY);&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&Mat&&&&&&Canny(I,contours,125,350);&&&&&threshold(contours,contours,128,255,THRESH_BINARY);&&&&&namedWindow(&Canny&);&&&&&imshow(&Canny&,contours);&&&&&waitKey();&&&&&return&0;&}&
显示效果如下:
498)this.width=498;' onmousewheel = 'javascript:return big(this)' border="0" alt="image" src="/wyfs02/M01/24/2F/wKiom1NMmv6BDuHiAABfjPbKgiI616.jpg" title="image" />
二、直线检测
直线在图像中出现的频率非常之高,而直线作为图像的特征对于基本内容的图像分析有着很重要的作用,本文通过OpenCV中的hough变换来检测图像中的线条。
我们先看最基本的Hough变换函数HoughLines,它的原型如下:
void&HoughLines(InputArray&image,&OutputArray&lines,&double&rho,&double&theta,&int&threshold,&double&srn=0,&double&stn=0&);&
它的输入是一个二值的轮廓图像,往往是边缘检测得到的结果图像;它的输出是一个包含多个Vec2f点的数组,数组中的每个元素是一个二元浮点数据 对&rou,theta&,rou代表直线离坐标原点的距离,theta代表角度。第3和第4个参数代表步长,因为Hough变换实际上是一 个穷举的算法,rho表示距离的步长,theta代表角度的步长。第5个参数是一个阈值设置直接的最低投票个数,知道Hough原理的,这个参数应该很容 易理解。
从 这个函数的输出结果我们可以看出,得到的直线并没有指定在图像中的开始点与结束点,需要我们自己去计算,如果我们想把直接显示在图像中就会比较麻烦,而且 会有很多角度接近的直线,其实它们是重复的,为了解决上面这些问题,OpenCV又提供了一个函数HoughLinesP()。它的输出是一个 Vector of
Vec4i。Vector每一个元素代表一条直线,是由一个4元浮点数组构成,前两个点一组,后两个点一组,代表了在图像中直线的起始和结束点。
void&HoughLinesP(InputArray&image,&OutputArray&lines,&double&rho,&double&theta,int&threshold,&double&minLineLength=0,&double&maxLineGap=0&);&
解释一下最后两个参数,minLineLength指定了检测直线中的最小宽度,如果低于最小宽度则舍弃掉,maxLineGap指定通过同一点的直线,如果距离小于maxLineGap就会进行合并。
下面是一个用HoughLinesP检测直线的例子:
int&main()&{&&&&&Mat&image=imread(&../car.png&);&&&&&Mat&I;&&&&&cvtColor(image,I,CV_BGR2GRAY);&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&Mat&&&&&&Canny(I,contours,125,350);&&&&&threshold(contours,contours,128,255,THRESH_BINARY);&&&&&vector&Vec4i&&&&&&&&&&&&HoughLinesP(contours,lines,1,CV_PI/180,80,50,10);&&&&&drawDetectLines(image,lines,Scalar(0,255,0));&&&&&namedWindow(&Lines&);&&&&&imshow(&Lines&,image);&&&&&waitKey();&&&&&return&0;&}&
上面程序将检测到的线条保存在lines变量内,我们需要进一步将它们画在图像上:
void&drawDetectLines(Mat&&image,const&vector&Vec4i&&&lines,Scalar&&&color)&{&&&&&&&&&&vector&Vec4i&::const_iterator&it=lines.begin();&&&&&while(it!=lines.end())&&&&&{&&&&&&&&&Point&pt1((*it)[0],(*it)[1]);&&&&&&&&&Point&pt2((*it)[2],(*it)[3]);&&&&&&&&&line(image,pt1,pt2,color,2);&&&&&&&&&&++&&&&&}&}&
498)this.width=498;' onmousewheel = 'javascript:return big(this)' width="538" height="302" border="0" style="margin:0padding:0border:0background-image:" alt="image" src="/wyfs02/M00/24/2F/wKioL1NMmtajB4TeAACAeZK_OnY105.jpg" title="image" />
实 际上Hough变换可以检测很多固定的形状,比如:圆、正方形等。它们的原理基本相同,都是构造一个投票矩阵。OpenCV里提供了检测圆的函数 HoughCircles,它的输出是一个Vector of
Vec3i,Vector的每个元素包含了3个浮点数,前2个是圆的中心坐标,最后一个是半径。
三、轮廓的提取与描述
在目标识别中我们首先要把感兴趣的目标提取出来,而一般常见的步骤都是通过颜色或纹理提取出目标的前景图(一幅黑白图像,目标以白色显示在图像中),接下来我们要对前景图进行分析进一步地把目标提取出来,而这里常常用到的就是提取目标的轮廓。
OpenCV 里提取目标轮廓的函数是findContours,它的输入图像是一幅二值图像,输出的是每一个连通区域的轮廓点的集 合:vector&vector&Point&&。外层vector的size代表了图像中轮廓的个数,里面vector的 size代表了轮廓上点的个数。下面我们通过实例来看函数的用法。
int&main()&&&{&&&&&&&using&namespace&&&&&&&&&&&&&&&&&&&&&Mat&image=imread(&../shape.png&);&&&&&&&cvtColor(image,image,CV_BGR2GRAY);&&&&&&vector&vector&Point&&&&&&&&&&&&&&&findContours(image,contours,CV_RETR_EXTERNAL,CV_CHAIN_APPROX_NONE);&&&&&&&&&&&Mat&result(image.size(),CV_8U,Scalar(0));&&&&&&drawContours(result,contours,-1,Scalar(255),2);&&&&&&&&&&&&&&&&&&namedWindow(&contours&);&&&&&&imshow(&contours&,result);&&&&&&waitKey();&&&&&&return&0;&}&
498)this.width=498;' onmousewheel = 'javascript:return big(this)' width="484" height="136" border="0" style="margin: 0 padding: 0 border: 0 background-image:" alt="image" src="/wyfs02/M00/24/2F/wKioL1NMmtbSQA-FAABVxNFPy28688.jpg" title="image" />
上面程序中包含了2个函数,第一个是查找轮廓函数,它的第三个参数说明查找轮廓的类型,这里我们使用的是外轮廓,还可以查找所有轮廓,即包括一些孔洞的部 分,像图像人物胳膊与腰间形成的轮廓。第4个参数说明了轮廓表示的方法,程序中的参数说明轮廓包括了所有点,也可以用其他参数让有点直线的地方,只保存直 线起始与终点的位置点,具体参数用法可以参考手册里函数的介绍。
第二个函数drawContours是一个画轮廓的函数,它的第3个参数程序里设置-1表示所有的轮廓都画,你也可以指定要画的轮廓的序号。
提取到轮廓后,其实我们更关心的是如果把这些轮廓转换为可以利用的特征,也就是涉及到轮廓的描述问题,这时就有多种方法可以选择,比如矢量化为多边形、矩形、椭圆等。OpenCV里提供了一些这样的函数。
&Rect&r&=&boundingRect(Mat(contours[0]));&rectangle(result,&r,&Scalar(255),&2);&&float&&Point2f&&minEnclosingCircle(Mat(contours[1]),&center,&radius);&circle(result,&Point(center),&static_cast&int&(radius),&Scalar(255),&2);&&vector&Point&&&approxPolyDP(Mat(contours[2]),&poly,&5,&true);&vector&Point&::const_iterator&itp&=&poly.begin();&while&(itp&!=&(poly.end()&-&1))&{&&&&&line(result,&*itp,&*(itp&+&1),&Scalar(255),&2);&&&&&++&}&line(result,&*itp,&*(poly.begin()),&Scalar(255),&2);&&vector&Point&&&convexHull(Mat(contours[3]),&hull);&vector&Point&::const_iterator&ith&=&hull.begin();&while&(ith&!=&(hull.end()&-&1))&{&&&&&line(result,&*ith,&*(ith&+&1),&Scalar(255),&2);&&&&&++&}&line(result,&*ith,&*(hull.begin()),&Scalar(255),&2);&
程序中我们依次画了矩形、圆、多边形和凸多边形。最终效果如下:
498)this.width=498;' onmousewheel = 'javascript:return big(this)' width="360" height="208" border="0" style="margin:0padding:0border:0background-image:" alt="image" src="/wyfs02/M02/24/2F/wKiom1NMmv-hMgzMAAAuzkQB9sY125.jpg" title="image" />
对连通区域的分析到此远远没有结束,我们可以进一步计算每一个连通区域的其他属性,比如:重心、中心矩等特征,这些内容以后有机会展开来写。
以 下几个函数可以尝试:minAreaRect:计算一个最小面积的外接矩形,contourArea可以计算轮廓内连通区域的面 积;pointPolygenTest可以用来判断一个点是否在一个多边形内。mathShapes可以比较两个形状的相似性,相当有用的一个函数。
【编辑推荐】
【责任编辑: TEL:(010)】
关于的更多文章
一款《Flappy Bird》捧红了越南开发者阮哈东,引来无数关注。小
在iOS深层开发中我们大都会遇到诸如多媒体,传感器相
移动办公模式是IT消费化的一个戏剧性结果。 这一模式
2013年手机游戏大火,但随着很多人涌入进来,同质化和
本书是根据全国计算机技术与软件专业技术资格(水平)考试的“计算机网络管理员考试大纲”所要求的考试范围而编写的辅导用书。全
Windows Phone专家
Android开发专家
51CTO旗下网站coreldraw x8 轮廓笔 CorelDRAW X8实现轮廓线的粗细变化的方法-平面设计-就爱阅读网
CorelDRAW X8实现轮廓线的粗细变化的方法
&  方法一:使用&轮廓笔&中的书法效果  1. 使用&贝塞尔 &工具绘制开放路径,在属性栏上的&轮廓宽度 &中设置轮廓宽度(或者也可以在&轮廓笔& 对话框中设置),效果如图所示。  2. 点击&轮廓笔 &工具,快捷键&F12&(如果在CDR X8工具箱中没有,可点击快速自定义,展开轮廓笔工具栏)。在&书法 &属性中设置&展开 &和&角度 &数值,该命令针对断开曲线,可以以书法字体的感觉创建粗细不均的轮廓和旋转倾斜角度,以实现轮廓线的粗细变化。  3. 设置&书法 &展开和角度数值之后,单击&确定 &按钮,即可对曲线段应用&书法 &效果,如图所示,您也可以尝试其他数值和角度。  提示:此种方法是随机变化。  方法二:利用将轮廓装换为形状命令  1. 在选择曲线段的状态下,执行&对象&将轮廓转换为曲线 &命令(快捷键&Ctrl+Shift+Q&),如图所示。  2. 此时的开发的曲线段已经变成了闭合的路径。  3. 使用&形状工具 &调整节点和手柄。  以上就是CorelDRAWX8实现轮廓线的粗细变化的两种方法介绍,操作很简单,不会的朋友可以参考本文,希望能对大家有所帮助!
邀请好友扫一扫分享给TA或者 长按上图保存二维码,使用微信扫一扫右上角的"相册"扫码,再分享好友或朋友圈OpenCV 2 轮廓检测与显示
OpenCV 2 轮廓检测与显示
发布时间: 14:46:25
编辑:www.fx114.net
本篇文章主要介绍了"OpenCV 2 轮廓检测与显示",主要涉及到OpenCV 2 轮廓检测与显示方面的内容,对于OpenCV 2 轮廓检测与显示感兴趣的同学可以参考一下。
一、函数讲解
1、findContours
函数说明:查找二值图像中的轮廓
函数原型:void findContours(InputOutputArray image, OutputArrayOfArrays contours, OutputArray hierarchy, int mode, int method, Point offset=Point())
void findContours(InputOutputArray image, OutputArrayOfArrays contours, int mode, int method, Point offset=Point())
参数说明:image 8位单通道图像。非零的像素为1的处理。零像素保持为0,因此,图像被视为二进制。可以使用compare() , inRange() , threshold() ,adaptiveThreshold() , Canny() ,函数提取的轮廓并修改图像。
contours 检测到的轮廓。每个轮廓的点被存在vector中。
hierarchy 可选的输出vector,包含图像的拓扑信息。它有许多元素等值线数目。对于每一个第i个轮廓的 contours[i] 元素hierarchy[i][0] , hiearchy[i][1] , hiearchy[i][2] ,和hiearchy[i][3] 被设定为0,基于轮廓的下一个和以前相同的元素层次指数,即:第一个子轮廓和它的父轮廓。如果轮廓i没有下一个,前一个和父轮廓的话,hierarchy[i] 元素是负的。
mode 轮廓检索模式:
CV_RETR_EXTERNAL 查找外边缘,各边缘以指针h_next相连,它设置所有的轮廓hierarchy[i][2=hierarchy[i][3]]=-1。
CV_RETR_LIST 检索所有的轮廓,并将其保存到一条链表当中。没有建立任何层次关系。
CV_RETR_CCOMP 检索所有的轮廓,并将他们组织为两层:顶层是各部分的外部边界,第二层是空洞的边界;如果有其他轮廓里面的孔的连接组件,它仍然是在顶层。
CV_RETR_TREE 检索所有的轮廓,并重构嵌套轮廓的整个层次。
method 轮廓近似方法:
CV_CHAIN_APPROX_NONE 存储绝对轮廓点。也就是说轮廓任意随后的两点(X1,Y1)和(X2,Y2)是水平,垂直或对角线邻域。也就是max(abs(x1-x2),abs(y2-y1))==1。
CV_CHAIN_APPROX_SIMPLE 压缩水平,垂直和对角线段,只留下他们的终点。例如,一个向上右矩形轮廓进行编码的4分。
CV_CHAIN_APPROX_TC89_L1,CV_CHAIN_APPROX_TC89_KCOS 适用the flavors of the Teh-Chin chain approximation algorithm
offset 可选偏移每一个轮廓点的偏移。如果从图像ROI中提取的轮廓,这是非常有用的。比如你要从图像的(100, 0)开始进行轮廓检测,那么就传入(100,0)。
注意事项:此函数使用算法[Suzuki85]从二值图像检索轮廓,对形状分析和目标检测与识别很有用。2、drawContours
函数说明:绘制轮廓线或填充轮廓。
函数原型:void drawContours(InputOutputArray image, InputArrayOfArrays contours, int contourIdx, const Scalar& color, int thickness=1, int lineType=8, InputArray hierarchy=noArray(),intmaxLevel=INT_MAX, Point offset=Point() )
参数说明:image 要绘制轮廓或填充轮廓的图像。
contours 所有的输入轮廓。每个轮廓存储为点vector。
contourIdx 参数指示轮廓绘制。如果是否,所有的轮廓绘制。
color 轮廓颜色
thickness 绘制轮廓线的粗度。如果是负数(例如,thickness= CV_FILLED的),绘制内部轮廓。
lineType 线路连接。有关详细信息,请参阅line()。
hierarchy 可选的层次信息。它是只需要如果你想只绘制部分的轮廓(见maxLevel)。
maxLevel 绘制轮廓的最高水平。如果是0,只有指定的轮廓绘制。如果是1,则该函数绘制的轮廓(s)和所有的嵌套的轮廓。如果为2,则该函数绘制的轮廓,所有的嵌套的轮廓,所有的嵌套到嵌套的轮廓, 等等。此参数时,只考虑有层次。
offset 可选轮廓移位参数。将所有绘制由指定的轮廓。比如你要从图像的(100, 0)开始进行轮廓检测,那么就传入(100, 0)。
注意事项:此函数绘制轮廓线(thickness &= 0)或者填充轮廓(thickness & 0)。
二、举例说明
#include &opencv2/highgui/highgui.hpp&
#include &opencv2/imgproc/imgproc.hpp&
#include &iostream&
#include &stdio.h&
#include &stdlib.h&
M Mat src_
int thresh = 100;
int max_thresh = 255;
RNG rng(12345);
/// 函数声明
void thresh_callback(int, void* );
int main( int argc, char** argv )
//导入图像
src = imread(&0.jpg&, 1 );
/// 转为灰度图,中值滤波
cvtColor( src, src_gray, CV_BGR2GRAY );
blur( src_gray, src_gray, Size(3,3) );
//创建窗口
char* source_window = &Source&;
namedWindow( source_window, CV_WINDOW_AUTOSIZE );
imshow( source_window, src );
createTrackbar( & Canny thresh:&, &Source&, &thresh, max_thresh, thresh_callback );
thresh_callback( 0, 0 );
waitKey(0);
return(0);
// 回调函数
void thresh_callback(int, void* )
Mat canny_
vector&vector&Point& &
vector&Vec4i&
/// 二值化
Canny( src_gray, canny_output, thresh, thresh*2, 3 );
findContours( canny_output, contours, hierarchy, CV_RETR_TREE, CV_CHAIN_APPROX_SIMPLE, Point(0, 0) );
//画出轮廓
Mat drawing = Mat::zeros( canny_output.size(), CV_8UC3 );
for( int i = 0; i& contours.size(); i++ )
Scalar color = Scalar( rng.uniform(0, 255), rng.uniform(0,255), rng.uniform(0,255) );
drawContours( drawing, contours, i, color, CV_FILLED, 8, hierarchy, 0, Point() );
namedWindow( &Contours&, CV_WINDOW_AUTOSIZE );
imshow( &Contours&, drawing );
}三、结果显示
& 结果如下图所示。
一、不得利用本站危害国家安全、泄露国家秘密,不得侵犯国家社会集体的和公民的合法权益,不得利用本站制作、复制和传播不法有害信息!
二、互相尊重,对自己的言论和行为负责。
本文标题:
本页链接:

我要回帖

更多关于 wifi万能钥匙 的文章

 

随机推荐