68.基于matlab的小波分解子模式和盒维数的车型识别可以选择不同车型,包括小车、中车、大车。 GUI可视化界面操作,已包括多种图片。 程序已调通,可直接运行。
先上个效果图镇楼(假装有图)------左边是各种车型的轮廓图,右边实时显示小波分解后的高频细节和盒维数计算结果。这玩意儿最爽的点在于,选个图片点两下就能看到算法怎么把车屁股轮廓拆解得明明白白。
搞车型识别这事儿,传统方法总在像素级特征上死磕。咱们换个思路,把小波分解的子模式特征和盒维数这个分形维度指标捏在一起,效果意外地能打。先说核心逻辑:不同车型的轮廓在高频子带的空间分布差异比肉眼看到的明显得多。
直接扒代码里的关键部分来看。预处理阶段有个骚操作,把图片转灰度后不是直接上小波,而是先做形态学梯度增强轮廓:
matlab
se = strel('disk',3);
img_processed = imdilate(img_gray,se) - imerode(img_gray,se);
这步操作相当于给车辆轮廓描了个3像素宽的边,实测比直接Canny边缘检测稳得多。接下来是小波分解的重头戏,用'db4'基函数做3层分解:
matlab
[c,s] = wavedec2(img_processed, 3, 'db4');
[H1,V1,D1] = detcoef2('all',c,s,1);
这里H1、V1、D1分别存着水平、垂直、对角线方向的高频细节。重点来了------子模式特征提取不是简单取均值,而是计算各方向系数的信息熵:
matlab
h1_entropy = entropy(H1(:));
v1_entropy = entropy(V1(:));
d1_entropy = entropy(D1(:));
这么搞是因为发现中大型车的水平方向熵值明显高于小车,而垂直方向刚好相反。至于盒维数计算,代码里用了个双重循环暴力求解:
matlab
for box_size = 2.^[4:0.5:7]
cnt = 0;
for i = 1:step:size(edge_img,1)
for j = 1:step:size(edge_img,2)
if any(edge_img(i:i+box_size-1,j:j+box_size-1),'all')
cnt = cnt + 1;
end
end
end
N_boxes(end+1) = cnt;
end
这个循环块看着糙但效率够用,实测处理640x480的图能在0.2秒内跑完。最后用polyfit拟合log(Nboxes)和log(1/boxsize)的斜率就是盒维数。
GUI设计部分藏了个彩蛋:双击特征图可以弹出该车型的小波分解三维视图(此处应有wireframe动图)。分类模块用最朴素的KNN反而比SVM效果好,估计是因为特征维度不高(总共就4个特征:3个熵值+盒维数)。
测试时发现个玄学现象------大货车的盒维数普遍在1.6-1.8之间,而家用轿车基本在1.3-1.5晃悠。这可能跟货车轮廓的锯齿状特征更明显有关。不过遇到改装车宽体套件时算法会懵,这时候得手动切到中级模式调整小波分解层数。
要说遗憾的话,没把实时摄像头采集做进去算是个痛点。但项目包里自带的23种车型样本够新手折腾一阵子了,从五菱宏光到擎天柱造型的货车都有(手动狗头)。跑不通的兄弟注意检查Matlab版本,R2018a以上得把imdilate的参数格式改改。
