图像轮廓生成Freeman码
##图像轮廓生成Freeman码##
- 摘要
Freeman码是描述轮廓的另外一种形式,这篇博客我将会用matlab和OpenCV两个版本生成Freeman码。纵观网上很多介绍边缘轮廓的,都提到过Freeman码,但是实现却比较少。
准备工作
2.1 matlab版
matlab自身是不带边界轮廓跟踪生成Freeman码算法函数的。起初我做的时候,网上有介绍matlab轮廓生成Freeman码函数,给个链接matlab生成Freeman码介绍,但是在matlab编辑器上写这个函数时,发现报错"未定义boundaries函数"。其实这个函数是书本《数字图像处理MATLAB版》的库函数,matlab不自带,故需要在matlab中添加库函数,我有资源冈萨雷斯数字图像MATLAB处理库函数,具体添加工作可以百度,也可以问我。
2.2 OpenCV版
OpenCV不需要准备工作。Freeman码的生成
3.1 matlab版
用matlab生成Freeman码的代码可以在我给出的那篇博客中复制过来,我把生成Freeman码的代码写进了一个function中,在以前基础上,我将每个轮廓点的和它的链码(即它下一个点在它的那个方向上)存起来以更好的下一步工作,代码如下:
function contours=freeman(im_edge)% 函数定义c=boundaries(im_edge,8);%生成Freeman码contours=cell(size(c,1),1);index=1;
% [L,W]=size(im_edge);%观察轮廓
% im_edge(c{1}(:,1)+(c{1}(:,2)-1)*L)=1;
% imshow(im_edge);while index<=size(c,1)if length(c{index})<40c(index)=[];elseh=fchcode(c{index,:},8);contour=c{index,1}(1:length(h.fcc),:);contour=[contour,h.fcc'];%提取Freeman并和轮廓点组合contours{index,1}=contour;index=index+1;endendcontours(index:end,:)=[];
end
调用上述函数代码:
contours=freeman(im_edge);
contours生成的Freeman就在元胞数组里,可以进行下一步工作了。另外,matlab语言我还不是很熟练,很多用法都是业余水平,望指教!
---------------------------------------------------------2019-03-27更新---------------------------------------------------------------
这两天做论文时发现,matlab中还有个提取轮廓链码的函数bwboundaries,具体的用法大家可以自行百度,我在这里想说的是,这个函数bwboundaries要比boundaries函数快三倍时间。bwboundaries好像是外部库函数,我用的是matlab2014b。
[c,l]= bwboundaries(im_edge,'noholes'); %c是基于八邻域提取的轮廓,
[cc]=chaincode(c{index,1}); %提取对应的Freeman链码
这个chaincode是在mathworks上搜的提取轮廓Freeman链码的一个function
我这里直接贴上来代码,有点多,好多注释,我直接放链接吧,看了下,好像作者更新了,应该也是没问题,如果想用我的,私信我即可。
[https://ww2.mathworks.cn/matlabcentral/fileexchange/29518-freeman-chain-code?s_tid=srchtitle]
---------------------------------------------------------end-----------------------------------------------------------------------------
3.2 OpenCV版
OpenCV自带轮廓提取的库函数是findContours(),这是C++接口函数,目前我还没有用findContours()函数生成Freeman码,这里我是使用C语言接口的函数cvFindContours(),但是这并不影响我们使用C++调用OpenCV的库函数。在这里感谢原帖如何取得Freeman链码,帖子上代码是没什么问题的,但是美中不足的是在提取轮廓点坐标时有错误,我自己摸索出解决方法,同样的,我也将提取Freeman码写进一个函数供调用,OpenCV生成Freeman码的代码如下:
void Freemans(Mat srcimage,vector<vector<FM>>&FMS)
{CvMat _srcimage = srcimage;CvMemStorage* storage = cvCreateMemStorage();//采用默认大小,即:0.CvSeq* first_contour = NULL;int Nc = cvFindContours(&_srcimage,storage,&first_contour,sizeof(CvContour),CV_RETR_CCOMP, CV_CHAIN_CODE,///*这个是关键参数*/cvPoint(0, 0));CvChain* chain = 0;vector<CvSeq*>c1;CvSeq* h;for( CvSeq* c = first_contour; c != NULL;c=c->h_next){vector<FM>fms;int total=c->total;if(total<20)c=c->h_next;else{CvSeqReader reader;cvStartReadSeq( (CvSeq*)c, &reader, 0 );CvChainPtReader reader1;cvStartReadChainPoints((CvChain*)c, &reader1);FM fm;for( int i = 0; i < total; i++ ){char code;CV_READ_SEQ_ELEM( code, reader ); //printf(" %d,",code); //得到轮廓的Freeman链码序列fm.direction=code;CvPoint pt;CV_READ_CHAIN_POINT(pt,reader1);fm.x=pt.x;fm.y=pt.y;fms.push_back(fm);}FMS.push_back(fms);}}//for
}
调用上述函数代码:
Freemans(dstimage,FMSS);
dstimage是用边缘检测算法检测出的边缘,FMSS是存放轮廓点及其Freeman码的容器,包含三个元素,你懂的。
至此,两个版本的轮廓生成Freeman码都写完了,无论是matlab还是OpenCV,两个版本的算法共同的缺点是对于非闭合轮廓会生成两遍,闭合轮廓是没问题的。我的另外一篇博客OpenCV八邻域轮廓跟踪算法同样的也可以生成Freeman码,但个人认为首选OpenCV自带的库函数还是比较好。
5. 总结
在生成Freeman码过程中,付出很多,查找很多资料,有时候看见网上一些关于轮廓生成Freeman的帖子蜻蜓点水就来气,没有实用的方法生成Freeman码,所以自己将自己得成果整理出来奉献出来相互学习交流,不足的地方望批评指正,谢谢大家!
图像轮廓生成Freeman码相关推荐
- 《OpenCV3编程入门》学习笔记八:图像轮廓与分割
一:内容介绍 本节主要介绍OpenCV的imgproc模块的图像轮廓与分割部分: 1. 查找并绘制轮廓 2. 寻找物体的凸包 3. 使用多边形将轮廓包围 4. 图像的矩 5. 分水岭算法 6. 图像修 ...
- CV-提取图像Freeman码python实现
在anaconda和python下提取图像的freeman码 先利用opencv中的cv2.findContours 函数描述图片的轮廓,然后再返回值中得到一个有关于图像轮廓的数组,因为我们要的是fr ...
- 解决PHP生成校验码时“图像因其本身有错无法显示”的错误
2019独角兽企业重金招聘Python工程师标准>>> 今天使用http://crazymud.iteye.com/blog/452293给出的代码进行PHP生成校验码功能的实现,发 ...
- OPENCV图像轮廓检测
前面在图像转换的时候学到canny算子,可以检测出图像的轮廓信息,但是,该算子检测到的轮廓信息还需要我们手动的用眼睛去识别,而实际工程应用中,我们需要得到轮廓的具体数学信息,这就涉及到今天的主题,图像 ...
- 《OpenCV3编程入门》学习笔记8 图像轮廓与图像分割修复(五)分水岭算法(watershed algorithm)
8.5 分水岭算法(watershed algorithm) 1.基于拓扑理论的数学形态学的分割方法. 2.基本思想:把图像看作测地学上的拓扑地貌,图像中每一点像素的灰度值表示该点的海拔高度,每一个局 ...
- 《OpenCV3编程入门》学习笔记8 图像轮廓与图像分割修复(四)图像的矩
8.4 图像的矩 从一幅数字图形中计算出来的矩集,通常描述了该图像形状的全局特征,并提供了大量关于该图像不同类型的几何特性信息,如大小.位置.方向.形状等 (1)一阶矩与形状有关 (2)二阶矩显示曲线 ...
- 【opencv】(6) 图像轮廓处理
各位同学好,今天和大家分享一下opencv中如何获取图像轮廓,以及对轮廓的一些其他操作.内容有: (1)轮廓检测:cv2.findContours():(2)轮廓绘制:cv2.drawContours ...
- 图像轮廓、凸包、图像的矩、分水岭算法、图像修补
文章目录 1.查找并绘制轮廓 1.1 寻找轮廓:findContours() 函数 1.2 绘制轮廓:drawContours() 函数 1.3 示例程序:轮廓查找 1.4 综合示例:查找并绘制轮廓 ...
- OpenCV检测图像轮廓
轮廓只不过是图像中连接的曲线,或者图像中连通部分的边界,轮廓通常以图像中的边缘来计算,但是,边缘和轮廓的区别在于轮廓是闭合的,而边缘可以是任意的.边缘的概念局限于点及其邻域像素,轮廓将目标作为整体进行 ...
最新文章
- 动漫风格迁移AnimeGANv2,发布线上运行Demo
- 滑动门和翻转门实现的横竖双tab标签测试页面(附源码)
- vue.js 动态添加组件
- 剑指offer试题(PHP篇一)
- 4.无监督学习--K-means聚类
- [Spring5]IOC容器_Bean管理注解方式_创建对象
- 1.10 编程基础之简单排序 04 奖学金 7分 python
- redis提示Could not get a resource from the pool(jedis连接池配置)
- Hbuilder启动夜神游模拟器失败,解决方案
- 助力春运 重庆机场今晨新增一架飞机入列
- jumpserver 跳板机
- (BFS)uva2554-Snakes Ladders
- 打印机服务器不存在修复,win10电脑安装打印机提示处理器不存在_win10添加打印机错误“打印处理器不存在的修复办法-爱纯净...
- mysql数据库题库和答案2016_哪位大侠可以提供一些mysql数据库的题库,一定要带答案的!将感激不尽!!...
- Shell脚本之shift用法
- 《JS修炼之道》—— 读后总结
- gensim corpora的简单使用
- 计算机二级考试字处理真题,计算机二级office字处理软件的重难点总结
- Windows 技术篇 - 杜比驱动安装,解决电脑渣渣音效!
- IOS KeyChain