当前位置: 首页 > news >正文

【机器视觉与图像处理】基于MATLAB的角度计算

正文之前

最近新开了一门课,我十分感兴趣,或者是说老早就想接触类似方面的学习,但是一直没有真正着手,所以说,其实上课还是很有必要的,很多时候你想做的事情但是你根本没法开始,所以需要一个推动力,当一点点的作业加上完成学分的压力压在你的肩头,配合你早就蓄势待发的兴趣使然,就会爆发很大的热情去学习。就好比这门,机器视觉与图像处理技术, 我很感兴趣,所以昨天坐火车的时候我都在火车上把我们这门课的第一次作业做出来了。

正文

我们的第一次作业,是把下图中的这个风扇扇叶一个叶片的角度计算出来。

我一开始还苦思冥想,不知道怎么才能提取出来这个因素,所以很是烦恼不知道该如何是好,但是昨天看了下群里面的说法,我瞬间就理通了。只要转变下思维,把图像看成一个二维数组配上每个元素的大小不同代表着颜色深浅的想法就好了

他已经做到了这一步,剩下的就是不知道如何处理这个图形的元素,但是,我虽然目前还是个菜鸡,但是我好歹也是要念计算机的博士的人啊!!!怎么会被这种小问题难到??不存在的!!下面请看我的表演:

然后,想法有了。手段也有了。对数组的处理,尤其是一堆的只是bool量的二维数组,简直不要太简单好么?都不需要for嵌套了,直接取两个X坐标作为定值定量的检测这两行的数据,不就好了?下面是那位同学的想法:

我觉得,这样是给自己增加了工作量,反而让matlab变轻松了啊。怎么能这样呢?不存在的!!所以还是直接让matlab去计算吧,直接用两点确定一条直线的方式,给两条直线分别求出来斜率,然后在视觉的绝对坐标系下转化为角度,最后就得到咯~~:

这之间还发生了一个小插曲,那就是我给我的MATLAB爸爸跪舔的时候,直接被打脸了

这脸打的啪啪响!!

所以,最后这就是我的代码咯~~

pic=imread('/Users/zhangzhaobo/program/MATLAB/First_work_angles.jpg'); %读取照片作为一个对象读入matlab 而不是简单的打开
bw=im2bw(pic); % 我们需要的不是一个RGB图像,而是一个二值化图像就好了。至于什么是二值化,就是说黑白照咯,一个像素点,要不就是黑的要不就是白的,所以就很好整!!
bw=edge(bw,'canny');  % 边缘提取,一个一直困扰我的地方,因为我还没看到这些点!
%下面的变量分别就是我取点的列数,至于Y1 Y2 就是行数,因为读取出来的图像有点问题
first_dot1=0;
first_dot2=0;
second_dot1=0;
second_dot1=0;
Y1=400;Y2=450;

% 从400行第一个点到第2440个点,分别取值,为了防止噪声干扰,我还特意的给了一个范围以及限制。

for i=1:2440
    if 700<i<1600
        if bw(Y1,i)==1
            if first_dot1>0
                second_dot1=i
            else
                first_dot1=i
            end
        end
    end
end

% 从450行第一个点到第2440个点,分别取值,为了防止噪声干扰,我还特意的给了一个范围以及限制。

for i=1:2440
    if 700<i<1600
        if bw(Y2,i)==1
            if first_dot2>0
                second_dot2=i
            else
                first_dot2=i
            end
        end
    end
end

%算出斜率,然后斜率转为角度,最后角度之差就是叶片的角度啦!

XieLv1=(first_dot1-first_dot2)/(Y1-Y2)
XieLv2=(second_dot1-second_dot2)/(Y1-Y2)
Angle=atan(XieLv1)*180/pi-atan(XieLv2)*180/pi
复制代码

我知道肯定还有很多可以优化的地方,但是目前来说么。实现了测试角度就好了么~~我现在在小妹子这儿的图书馆陪她过双十一,美滋滋啊,图书馆人好多,但是排插好少,而且灯光是昏黄的,让人想睡觉!中评吧!

最后得出来的角度是44.4190°

之后我也测试了别的行数的数据,基本是形成了45°左右的正态分布,至于更大的数据,我就懒得算了,其实也可以写个小函数,统计下各个行数的时候会形成很多个值,然后求个平均 mean就好了!

还别说,偏差真的很大,我在想要不要真的写个统计函数,然后画个图给老师看?搞不好有加分?

或者把很多点存起来,来个线性回归分析???but ,我还是先看书吧,这些都是随便查得到的东西,就先不玩了!反正还没到交作业的时候不是。

正文之后

有木有人要资源啊,matlab的或者别的都行哦,我现在看不完了。mmp,感觉自己真是个盗版文化的传播者,but这些都是老掉牙的东西了。最新的都是2013的书了。再不找点人看估计都会灭绝吧!

书名我都给你准备好了。就怕你搜不到~

MATLAB+R2014a完全自学一本通 MATLAB图像处理.pdf MATLAB R2016a完全自学一本通附赠电子书.pdf 精通Matlab数字图像处理与识别 [张铮,倪红霞编著][人民邮电出版社][2013.04] 冈萨雷斯数字图像处理MATLAB版.中文版(第二版)2

(PS:当然,上面都是没法下载的,只是给你看看简介而已,要的点了喜欢后评论发邮箱,不过分吧?~~)


=========修改版========

Find_Angle.m

function [y]=Find_Angle(Y1,Y2,bw)
%下面省略的原因是一开始只准备测试一个角度,所以就单纯的在一个m文件里面导入对象,后来需要另外封装下传入边缘检测后的bw对象作为实参
%pic=imread('/Users/zhangzhaobo/program/MATLAB/First_work_angles.jpg');
% bw=im2bw(pic);
% bw=edge(bw,'canny'); 

% 按照我的四点构成两直线的做法,下面分别是四个点的列数,行数在形参中传入
first_dot1=0;
first_dot2=0;
second_dot1=0;
second_dot2=0;
% 遍历给定行所有的item,然后查找400-1300之间的元素(取点不可能在此范围外),取两点
for i=1:1600
    if (400 < i) && (i < 1300)
        if bw(Y1,i)==1
            if first_dot1>0  % 如果已经取过第一个点;那么就取第二个同一行内的点
                second_dot1=i;
            else
                first_dot1=i; % 如果没有取过第一个点,那么就记录第一个点
            end
        end
    end
end

% 相同步骤取第二行中的数据

for i=1:1600
    if (400 < i) && (i < 1300)
        if bw(Y2,i)==1
            if first_dot2>0
                second_dot2=i;
            else
                first_dot2=i;
            end
        end
    end
end

% 直接两点求斜率
XieLv1=(first_dot1-first_dot2)/(Y1-Y2);
XieLv2=(second_dot1-second_dot2)/(Y1-Y2);

% 绝对坐标系中由斜率算出绝对角度,然后相减得到相对角度
Angle=atan(XieLv1)*180/pi-atan(XieLv2)*180/pi;
% 判断Angle是否合理,配合调用此函数的内容可以进行筛选
if (Angle>49) || (Angle<43)
    y=0;
else
    y=Angle;
end
复制代码

Average.m

function [angle]=Average(pic) % 此函数用于求同一个扇叶的多次取点求直线夹角的过程
angle=0;  %初始化角度
count=0;  % 计数,用于最后的求平均
for i=(380:450)   % 我取 400行到500行之间的两行,间隔最小20 最大50 ,间隔步长为2
    for j=(20:2:50)
        if Find_Angle(i,i+j,pic)==0  % 如果求出很大偏差的角度,直接剔除
            continue;
        else
            angle=angle+Find_Angle(i,i+j,pic);
            count=count+1;
        end
    end
end
angle=angle/count;  % 求平均,完成一个扇叶的角度平均 1050次
复制代码

Find_4_Angles.m

clear; % 这个是总函数,类似于main 所以事前清除其他变量很有必要。
%读取对象并且进行最有阈值的筛选,二值化,边缘提取,删掉边缘利于旋转叶片
pic=imread('First_work_angles.jpg');
thresh=graythresh(pic);
bw=im2bw(pic,thresh);
bw=edge(bw,'canny'); 
BW=bw(100:1700,420:2020);
%建立角度数组,存储四个叶片的角度
Angle=[0,0,0,0];
%每次求得角度后转过90°再次求平均值
for i = 0:3
    BW=imrotate(BW,i*90);
    Angle(i+1)=Average(BW);
end
% 精度精确至3位有效数组,即0.1°
digits(3)
Angles=vpa(Angle,3)
复制代码

文件结构如图:

运行的时候直接输入Find_4_Angles即可!

相关文章:

  • 【毕设进行时-工业大数据,数据挖掘】用C++对数据进行整改,修缮一下!
  • JDBC
  • 动画演示 Delphi 2007 IDE 功能[4] - 自定义界面
  • ASCSDK-------通用包接入文档(UNITY篇)
  • 内存管理[3]
  • Graphics 单元下的公用函数目录
  • 入口文件开始,分析Vue源码实现
  • hive可以drop所有表的bug fix
  • 标准化 归一化
  • MongoDB命令
  • 【转】nGrinder 简易使用教程
  • (备忘)Java Map 遍历
  • Linux vmstat命令实战详解
  • LintCode 31. partitionArray 数组划分
  • ASP.NET-FineUI开发实践-6(二)
  • (三)从jvm层面了解线程的启动和停止
  • “寒冬”下的金三银四跳槽季来了,帮你客观分析一下局面
  • 【每日笔记】【Go学习笔记】2019-01-10 codis proxy处理流程
  • css的样式优先级
  • es的写入过程
  • Java Agent 学习笔记
  • Javascript设计模式学习之Observer(观察者)模式
  • JS函数式编程 数组部分风格 ES6版
  • k8s 面向应用开发者的基础命令
  • Nacos系列:Nacos的Java SDK使用
  • Redis学习笔记 - pipline(流水线、管道)
  • Webpack入门之遇到的那些坑,系列示例Demo
  • 包装类对象
  • 工作踩坑系列——https访问遇到“已阻止载入混合活动内容”
  • 精益 React 学习指南 (Lean React)- 1.5 React 与 DOM
  • 前端存储 - localStorage
  • 前嗅ForeSpider中数据浏览界面介绍
  • 如何优雅的使用vue+Dcloud(Hbuild)开发混合app
  • 实战|智能家居行业移动应用性能分析
  • #FPGA(基础知识)
  • #在线报价接单​再坚持一下 明天是真的周六.出现货 实单来谈
  • $(function(){})与(function($){....})(jQuery)的区别
  • (C语言)球球大作战
  • (差分)胡桃爱原石
  • (原創) 是否该学PetShop将Model和BLL分开? (.NET) (N-Tier) (PetShop) (OO)
  • (转)http协议
  • (转)MVC3 类型“System.Web.Mvc.ModelClientValidationRule”同时存在
  • (转)scrum常见工具列表
  • ... fatal error LINK1120:1个无法解析的外部命令 的解决办法
  • .NET CORE 第一节 创建基本的 asp.net core
  • .NET Core 实现 Redis 批量查询指定格式的Key
  • .NET 使用 JustAssembly 比较两个不同版本程序集的 API 变化
  • .net程序集学习心得
  • .Net调用Java编写的WebServices返回值为Null的解决方法(SoapUI工具测试有返回值)
  • .net之微信企业号开发(一) 所使用的环境与工具以及准备工作
  • @reference注解_Dubbo配置参考手册之dubbo:reference
  • @vue/cli脚手架
  • [ C++ ] STL---string类的模拟实现
  • [ vulhub漏洞复现篇 ] Celery <4.0 Redis未授权访问+Pickle反序列化利用
  • [AIGC codze] Kafka 的 rebalance 机制