首先说一下我的经历吧!不想看的可以直跳到教程。之前在树莓派上训练分类器,发现树莓派内存过小,训练几张照片还ok,但是训练十几张照片进程直接就被系统扼杀掉,,所以这次选择用笔记本训练。经过测试,用400张50分辨率的正样本,1500张负样本训练,训练器级数为20,featureType 采用LBP特征时,需要4、5个小时才训练到16级,如果用Haar特征的话我训练的三天三夜才训练到16级,越是到后面越慢(featureType ,提取图像特征的类型,目前只支持LBP、HOG、Haar三种特征。但是HAAR训练非常非常的慢,而LBP则相对快很多)。还有我们安装的OpenCV是不带opencv_createsamples.exe和opencv_traincascade.exe这两个程序的,在网上找了很多的方法去编译然而只编译到opencv_createsamples.exe,后来我干脆不自己编译了,直接拿了别然的这两个exe程序来用。总之一句话就是“坑爹!”,太耗时间和精力了,下面教程我就用几张照片做个示范给你们看,如果你们跟着我来做的话是很快就能够完成的。
为了减少不必要的麻烦就不用源码安装了,直接在Powershell用pip安装,而且用国内源(我这里用的是阿里源)下载OpenCV,官方的太慢了。
打开Powershell,输入以下命令
pip install opencv-python -i http://mirrors.aliyun.com/pypi/simple/ --trusted-host mirrors.aliyun.com
测试一下
python
import cv2
pip install scikit-image
测试一下
import skimage.io as io
训练过分类器的小伙伴都知道,训练分类器需要用到opencv_createsamples.exe和opencv_traincascade.exe这两个程序,然而我们安装的OpenCV都是不带这两个程序的,这里呢我也是直接拿别人的来用的,两个文件下载链接如下:
链接: https://pan.baidu.com/s/1x5ZYDu5UP-CBOOjdcvbV2w
提取码:op5m
新建一个全英文目录下的文件夹OpenCV,下载后解压到该文件夹下,我的如下:
在opencv_bin下我们就可以找到opencv_createsamples.exe和opencv_traincascade.exe这两个文件,当然里面还包含了一些库,我们训练时是要用到他们的。
在OpenCV下新建两个文件夹分别为pos、neg,用来存放正样本和负样本图片。
1、收集并处理正样本
将正样本图片转为灰度图,并剪成合适的尺寸,方便后续处理。在OpenCV下创建1.py文件,放进下面代码并运行
import os
from skimage.color import rgb2gray
import numpy as np
import skimage.io as io
import cv2
def convert_gray(f, **args): # 图片处理与格式化的函数
rgb = io.imread(f) # 读取图片
gray = rgb2gray(rgb) # 将彩色图片转换为灰度图片
dst = cv2.resize(gray, (60, 60)) # 调整大小,图像分辨率为40*40
return dst
if __name__ == '__main__':
'''
批量转灰度图
'''
datapath = r'D:\OpenCV\pos' # 图片所在的路径
str = datapath + '/*.jpg' # 识别.jpg的图像
coll = io.ImageCollection(str, load_func=convert_gray) # 批处理
for i in range(len(coll)):
io.imsave('D:\OpenCV\pos\\' + np.str(i) + '.jpg', coll[i]) # 保存图片
可以看到正样本已经进行灰度、分辨率及顺序编号处理,注意:我们要把之前的彩色正样本删掉,不然在同一个文件夹下会影响后续训练。
2、收集负样
关于负样本,放到neg下即可,只要不含有正样本图片即可,最好是识别场景的图片。给大家一个负样本下载链接: https://pan.baidu.com/s/1TgyAuhuggktrZuWBFonUwQ提取码:j5q2,下载后如图,2000多张,已处理好灰度。
在OpenCV下建立2.py拷贝以下代码进去运行,生成正样本描述文件info.txt
import os
def create_pos_n_neg():
for file_type in ['pos']: #此处修改neg或pos即可
for img in os.listdir(file_type):
if (file_type == 'neg'):
line = file_type + '/' + img + '\n'
with open('bg.txt', 'a') as f:
f.write(line)
elif (file_type == 'pos'):
line = file_type + '/' + img + ' 1 0 0 50 50\n'
with open('info.txt', 'a') as f:
f.write(line)
if __name__ == '__main__':
create_pos_n_neg()
print('描述文件已生成!')
在OpenCV下建立3.py文件,拷贝下面代码,生成负样本描述文件bg.txt
import os
def create_pos_n_neg():
for file_type in ['neg']: #此处修改neg或pos即可
for img in os.listdir(file_type):
if (file_type == 'neg'):
line = 'D:/OpenCV/'+file_type + '/' + img + '\n'
with open('bg.txt', 'a') as f:
f.write(line)
elif (file_type == 'pos'):
line = 'D:/OpenCV/'+file_type + '/' + img + ' 1 0 0 50 50\n'
with open('info.txt', 'a') as f:
f.write(line)
if __name__ == '__main__':
create_pos_n_neg()
print('描述文件已生成!')
在cmd下进入D:\OpenCV\opencv_bin目录下运行下面命令
opencv_createsamples.exe -vec D:\OpenCV\info.vec -info D:\OpenCV\info.txt -bg D:\OpenCV\bg.txt -num 5 -w 50 -h 50
其中,-info字段填写正样本描述文件;-vec用于保存制作的正样本;-num制定正样本的数目,不能大于正样本图片数;-w和-h分别指定正样本的宽和高。
在OpenCV文件夹下建立xml_file文件夹,用来存储训练过程中生成的xml文件。
在cmd下进入D:\OpenCV\opencv_bin目录下运行下面命令
opencv_traincascade.exe -data D:\OpenCV\xml_file -vec D:\OpenCV\info.vec -bg D:\OpenCV\bg.txt -numPos 4 -numNeg 100 -numStages 5 -featureType LBP -w 50 -h 50
data :训练后data目录下会存储训练过程中生成的文件
vec :通过opencv_createsamples生成的vec文件
bg bg.txt:bg.txt是负样本文件的数据
numPos :正样本的数目,这个数值一定要比准备正样本时的数目少,不然会报can not get new positive sample.
numNeg :负样本数目,数值可以比负样本大
numStages :训练分类器的级数
w 50:必须与opencv_createsample中使用的-w值一致
h 50:必须与opencv_createsample中使用的-h值一致
featureType LBP: 训练时,提取图像特征的类型,目前只支持LBP、HOG、Haar三种特征。但是HAAR训练非常非常的慢,而LBP则相对快很多,因为HAAR需要浮点运算,精度自然比LBP更高,但是LBP的效果也基本能达到HAAR的效果。
注意:同时正负样本数目和w、h以及训练级数numStages的大小对训练时间的影响特别大
训练完之后我们就可以在xml_file文件夹下看到训练好的分类器cascade.xml
大功告成,有问题下方留言,谢谢!
参考:
链接: https://blog.csdn.net/MangoHHHH/article/details/109189666
链接: https://www.freesion.com/article/79671247590/