最近把一个ssd网络的net..prototxt网络结构和自己生成的hdf5格式数据一起做训练时发现经常报错,因为ssd中一些层在caffe中并没有实现,需要自己写相应的.cpp,.cu文件重新编译,比较麻烦,而大家通常训练caffe-ssd都是基于原作者公开的代码训练的,该代码中实现了这些层,于是把原作者代码跑了一遍.
我的机器是ubuntu16.04,装有两块GTX 1080TI 的显卡,一共20多个G显存,opencv是自己编译的3..3.0版本.
因为我机器主目录下已经有个装好的caffe了,所以再次在另一个目录下载该源码,该源码下载后编译也能import caffe,其他caffe项目也可以使用,如果没有装caffe,那就下载编译这个源码就能当做caffe使用,同时也能训练ssd.
1,先进入我这次操作的主目录(/home/user/yjf),下载源码
git clone https://github.com/weiliu89/caffe.git
cd caffe
git checkout ssd(切换到ssd分支)
这时候我的工作目录为 /home/user/yjf/caffe.然后执行如下操作
cp Makefile.config.example Makefile.config
然后参考我前面博客说过的如何搭建caffe环境文章中的说法更改Makefile和Makefile.config文件,并参照里面提到的方法进行编译(我感觉caffe不管是cpu还是gpu编译起来其实很简单的,我一般30分钟就能弄好,没有大家想象中的有难度或者难装,我用的python2.7,opencv3.3.0,cudnn7.3, cuda8.0,我使用cuda9.0报错,看来cuda9.0不匹配)
2,下载预训练模型,这个模型在我们训练ssd的时候作为初始化模型,我放在百度云了,https://pan.baidu.com/s/11JcopVftsLELIUSYmt-8Bw,大家下载即可.下载后放在/home/user/yjf/caffe/models/VGGNet目录,如果没有VGGNet目录就新建一个.
3,下载VOC2007和VOC2012数据集,放到/caffe/data目录下,并解压(其实没多大,几个G而已)
cd data
wget http://host.robots.ox.ac.uk/pascal/VOC/voc2012/VOCtrainval_11-May-2012.tar
wget http://host.robots.ox.ac.uk/pascal/VOC/voc2007/VOCtrainval_06-Nov-2007.tar
wget http://host.robots.ox.ac.uk/pascal/VOC/voc2007/VOCtest_06-Nov-2007.tar
tar -xvf VOCtrainval_11-May-2012.tar
tar -xvf VOCtrainval_06-Nov-2007.tar
tar -xvf VOCtest_06-Nov-2007.tar
4,把下载的数据转成训练需要的lmdb文件,在/home/user/yjf/caffe目录下执行
./data/VOC0712/create_list.sh当然,可以会报错的,打开这个文件,把第一行的root_dir换成root_dir=/home/user/yjf/caffe/data/VOCdevkit(你下载的VOCdevkit在哪里这个就换成那个目录就好,其他地方不改)
我改了原来代码中的3,5,41行,分别加了#yjf注释,我的放在这里,可以下载看下https://pan.baidu.com/s/1AETTYyjyKAnuKi27kE12Og
然后进行重新执行.执行结束后把data/VOC0712/create_data.sh里面的第七行root_dir换成root_dir=/home/user/yjf/caffe,注释掉cur_dir,data_root_dir="$root_dir/data/VOCdevkit")
然后执行./data/VOC0712/create_data.sh(执行前先在script/crerate_annoset.py中添加如下
import sys
sys.path.insert(0,'/home/user/yjf/caffe/python'))
5.然后在caffe目录下执行
python examples/ssd/ssd_pascal.py开始ssd训练,(训练过程可能报错SSD from caffe.proto import caffe_pb2 ImportError: No module named caffe.proto,解决:打开 caffe/scripts/create_annoset.py 文件,在from caffe.proto import caffe_pb2这段话之前加上
import sys
sys.path.insert(0,'/home/user/yjf/caffe/python')(这是刚刚安装的ssd-caffe的目录下的python目录)目标是让程序知道caffe在哪里.
另外,打开caffe/examples/ssd/ssd_pascal.py,看到gpus='0,1,2,3' 该成gpus='0',是指定训练使用的gpu,我用的0,然后python caffe/examples/ssd/ssd_pascal.py开始训练
训练过程如下图
(题外话:一般caffe需要net.prototxt和solver.prototxt,train.sh三个训练模型对吧,这次好像没看到,其实啊,caffe的这些net.prototxt网络结构文件是一般通过.py文件生成的,该代码中也是在训练的代码中先生成了这些东西,这些东西在/home/user/yjf/caffe/models/VGGNet/VOC0712/SSD_300x300目录下放着,train.prototxt和test.prototxt就是训练和测试的网络结构,同时人家还生成了deploy.prototxt文件,而solver.prototxt中存放了训练的超参数,snapshot: 8000指定训练8000个iters保存一次,我嫌弃时间太长,我想100次保存一个先看下结果,不过没到怎么改,然后我就等训练代码跑起来后在把程序停掉,这样就生成了这些文件,我直接在solver.prototx文件中改snapshot为100,然后写了一个train.sh文件,内容如下:
#!/usr/bin/env sh
set -e
# /home/user/caffe/build/tools/caffe train --solver=./solver.prototxt --gpu 1
/home/user/yjf/caffe/build/tools/caffe train --solver=./solver.prototxt --gpu 1
然后我在caffe/models/VGGNet/VOC0712/SSD_300x300目录直接执行sh ./tran.sh就开始训练了,训练的模型根据指定目录也在这个目录,大家可以不用这样,仅供参考
题外话结束####)
6,测试训练结果
在caffe目录执行
python examples/ssd/score_ssd_pascal.py,执行前先在该程序中的import caffe之前加上
import sys
caffe_root = '/home/user/yjf/caffe/'
sys.path.insert(0,caffe_root+'python')
目标是为了让程序找到caffe安装目录.测试结束如下
Test net outpu的值一般为0.7左右吧,我这个值低是因为我刚刚开始训练,我跑了100个iters就把模型保存起来试了一下,使用效果肯定低,模型需要跑二十多万个iters这个值就上去了.
源码提供了在视频和摄像头上的测试,
在视频上测试
python examples/ssd/ssd_pascal_video.py
直接运行这段代码就可以在视频预测,默认视频路径为examples/videos下面有一个视频,效果如下
在摄像头上测试
python examples/ssd/ssd_pascal_webcam.py如果报错就按照第6点在代码中添加caffe的目录就好
7,预测
caffe目录执行python examples/ssd/ssd_detect.py --model_weights ../VGG_VOC0712_SSD_300x300_iter_120000.caffemodel(此处为你训练的模型地址) --image_files /home/user/yjf/caffe/examples/images/fish-bike.jpg即可在caffe目录生成一个detect_result.jpg图片为检测结果,预测之前在该代码开头部分参照第6点添加caffe目录,要不然报错
经过一个晚上的训练,用新模型预测一下,效果如下图所示:
至此caffe-ssd测试结果,接下来将讲解使用直接的数据训练ssd