caffe框架下目标检测——faster-rcnn实战篇操作
原有模型
1、下載fasrer-rcnn源代碼并安裝
git clone --recursive https://github.com/rbgirshick/py-faster-rcnn.git
1)? 經(jīng)常斷的話,可以采取兩步:
git clone https://github.com/rbgirshick/py-faster-rcnn.git
2)? 到py-faster-rcnn中,繼續(xù)下載caffe-faster-rcnn,采取后臺跑:
git submodule update --init –recursive
2、編譯cython模塊
在py-faster-rcnn/lib目錄下,運(yùn)行以下命令:
Make
3、編譯caffe和pycaffe
在py-faster-rcnn/caffe-faster-rcnn下,編譯
make clean
make all –j16
make test
make runtest
注意:由于py-faster-rcnn使用python層,在Makefile.config中把WITH_PYTHON_LAYER:=1
我的環(huán)境會使用
4、下載模型:
Sh? data/scripts/fetch_faster_rcnn_models.sh
5、運(yùn)行基于python的demo
執(zhí)行以下命令:
Python tools/demo.py
6、下載訓(xùn)練、測試數(shù)據(jù)集
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
wget http://host.robots.ox.ac.uk/pascal/VOC/voc2007/VOCdevkit_08-Jun-2007.tar
?
tar xvf VOCtrainval_06-Nov-2007.tar
tar xvf VOCtest_06-Nov-2007.tar
tar xvf VOCdevkit_08-Jun-2007.tar
?
7、為了PASCAL VOC創(chuàng)建symlinks,創(chuàng)建軟連接
ln -s VOCdevkit VOCdevkit2007
?
遇到的問題見caffe框架下目標(biāo)檢測——faster-rcnn實戰(zhàn)篇問題集錦
?
工程目錄介紹
?
caffe-fast-rcnn —> caffe框架
data —> 存放數(shù)據(jù),以及讀取文件的cache
experiments —>存放配置文件以及運(yùn)行的log文件,配置文件
lib —> python接口
models —> 三種模型, ZF(S)/VGG1024(M)/VGG16(L)
output —> 輸出的model存放的位置,不訓(xùn)練此文件夾沒有
tools —> 訓(xùn)練和測試的python文件
?
訓(xùn)練模型需要修改的部分:
data —> 存放數(shù)據(jù),以及讀取文件的cache
models —> 三種模型, ZF(S)/VGG1024(M)/VGG16(L)
lib —> python接口
?
開始訓(xùn)練部分:
experiments —>存放配置文件以及運(yùn)行的log文件,配置文件
?
用模型測試/實驗結(jié)果部分:
tools —> 訓(xùn)練和測試的python文件
?
數(shù)據(jù)集
?
參考VOC2007的數(shù)據(jù)集格式,主要包括三個部分:
?
JPEGImages
Annotations
ImageSets/Main
JPEGImages —> 存放你用來訓(xùn)練的原始圖像
?
Annotations —> 存放原始圖像中的Object的坐標(biāo)信息,XML格式
?
ImageSets/Main —> 指定用來train,trainval,val和test的圖片的編號
?
JPEGImages
?
把圖片放入,但是有三點(diǎn)注意:
?
編號要以6為數(shù)字命名,例如000034.jpg
圖片要是JPEG/JPG格式的,PNG之類的需要自己轉(zhuǎn)換下
圖片的長寬比(width/height)要在0.462-6.828之間,就是太過瘦長的圖片不要
0.462-6.828,總之長寬比太大或者太小的,注意將其剔除,否則可能會出現(xiàn)下面實驗錯誤:
?
Traceback (most recent call last):
File “/usr/lib/python2.7/multiprocessing/process.py”, line 258, in _bootstrap
self.run()
File “/usr/lib/python2.7/multiprocessing/process.py”, line 114, in run
self._target(*self._args, **self._kwargs)
File “./tools/train_faster_rcnn_alt_opt.py”, line 130, in train_rpn
max_iters=max_iters)
File “/home/work-station/zx/py-faster-rcnn/tools/../lib/fast_rcnn/train.py”, line 160, in train_net
model_paths = sw.train_model(max_iters)
File “/home/work-station/zx/py-faster-rcnn/tools/../lib/fast_rcnn/train.py”, line 101, in train_model
self.solver.step(1)
File “/home/work-station/zx/py-faster-rcnn/tools/../lib/rpn/anchor_target_layer.py”, line 137, in forward
gt_argmax_overlaps = overlaps.argmax(axis=0)
ValueError: attempt to get argmax of an empty sequence
Google給出的原因是 Because the ratio of images width and heights is too small or large,這個非常重要
?
Annotations
?
faster rcnn訓(xùn)練需要圖像的bounding box信息作為監(jiān)督(ground truth),所以你需要將你的所有可能的object使用框標(biāo)注,并寫上坐標(biāo),最終是一個XML格式的文件,一個訓(xùn)練圖片對應(yīng)Annotations下的一個同名的XML文件
?
參考官方VOC的Annotations的格式:
<annotation>
??? <folder>VOC2007</folder>#數(shù)據(jù)集文件夾
??? <filename>009963.jpg</filename>#圖片的name
??? <source>#注釋信息,無所謂有無
?????? <database>The VOC2007 Database</database>
?????? <annotation>PASCAL VOC2007</annotation>
?????? <image>flickr</image>
?????? <flickrid>65163277</flickrid>
??? </source>
??? <owner>#注釋信息,無所謂有無
?????? <flickrid>Jez_P</flickrid>
?????? <name>Jeremy Pick</name>
??? </owner>
??? <size>#圖片大小
?????? <width>374</width>
?????? <height>500</height>
?????? <depth>3</depth>
??? </size>
??? <segmented>0</segmented>
??? <object>#多少個框就有多少個object標(biāo)簽
?????? <name>car</name>#bounding box中的object的class name
?????? <pose>Frontal</pose>
?????? <truncated>1</truncated>
?????? <difficult>0</difficult>
?????? <bndbox>
?????????? <xmin>2</xmin>#框的坐標(biāo)
?????????? <ymin>3</ymin>
?????????? <xmax>374</xmax>
?????????? <ymax>500</ymax>
?????? </bndbox>
??? </object>
</annotation>
這里有一個非常好用的工具VOC框圖工具,可以自動幫你生成需要的XML格式,實際中發(fā)現(xiàn)格式基本無誤,只有小的地方需要改動下
?
https://github.com/tzutalin/labelImg
?
Imagesets/Main
?
因為VOC的數(shù)據(jù)集可以做很多的CV任務(wù),比如Object detection, Semantic segementation, Edge detection等,所以Imageset下有幾個子文件夾(Layout, Main, Segementation),修改下Main下的文件 (train.txt, trainval.txt, val.txt, test.txt),里面寫上你想要進(jìn)行任務(wù)的圖片的編號
?
將上述你的數(shù)據(jù)集放在py-faster-rcnn/data/VOCdevkit2007/VOC2007下面,替換原始VOC2007的JPEGIMages,Imagesets,Annotations
?
代碼修改
?
修改源文件
?
faster rcnn有兩種各種訓(xùn)練方式:
?
Alternative training(alt-opt)
Approximate joint training(end-to-end)
推薦使用第二種,因為第二種使用的顯存更小,而且訓(xùn)練會更快,同時準(zhǔn)確率差不多,兩種方式需要修改的代碼是不一樣的,同時faster rcnn提供了三種訓(xùn)練模型,小型的ZFmodel,中型的VGG_CNN_M_1024和大型的VGG16,論文中說VGG16效果比其他兩個好,但是同時占用更大的GPU顯存(~11GB)
?
我使用的是VGG16 model + alternative training,需要檢測的類別四類,加上背景所以總共是五類
1 、py-faster-rcnn/models/pascal_voc/VGG16/faster_rcnn_alt_opt/stage1_fast_rcnn_train.pt
?
layer {?
? name: 'data'?
? type: 'Python'?
? top: 'data'?
? top: 'rois'?
? top: 'labels'?
? top: 'bbox_targets'?
? top: 'bbox_inside_weights'?
? top: 'bbox_outside_weights'?
? python_param {?
??? module: 'roi_data_layer.layer'?
??? layer: 'RoIDataLayer'?
??? param_str: "'num_classes': 5" #按訓(xùn)練集類別改,該值為類別數(shù)+1?
? }?
}?
?
layer {?
? name: "cls_score"?
? type: "InnerProduct"?
? bottom: "fc7"?
? top: "cls_score"?
? param {
? lr_mult: 1.0
? }?
? param {
? lr_mult: 2.0
? }?
? inner_product_param {?
??? num_output: 5 #按訓(xùn)練集類別改,該值為類別數(shù)+1?
??? weight_filler {?
????? type: "gaussian"?
????? std: 0.01?
??? }?
??? bias_filler {?
????? type: "constant"?
????? value: 0?
??? }?
? }?
}?
?
layer {?
? name: "bbox_pred"?
? type: "InnerProduct"?
? bottom: "fc7"?
? top: "bbox_pred"?
? param {
? lr_mult: 1.0
? }?
? param {
? lr_mult: 2.0
? }?
? inner_product_param {?
??? num_output: 20 #按訓(xùn)練集類別改,該值為(類別數(shù)+1)*4,四個頂點(diǎn)坐標(biāo)?
??? weight_filler {?
????? type: "gaussian"?
????? std: 0.001?
??? }?
??? bias_filler {?
????? type: "constant"?
????? value: 0?
??? }?
? }?
}?
?
2 、py-faster-rcnn/models/pascal_voc/VGG16/faster_rcnn_alt_opt/stage1_rpn_train.pt
?
layer {?
? name: 'input-data'?
? type: 'Python'?
? top: 'data'?
? top: 'im_info'?
? top: 'gt_boxes'?
? python_param {?
??? module: 'roi_data_layer.layer'?
??? layer: 'RoIDataLayer'?
??? param_str: "'num_classes': 5" #按訓(xùn)練集類別改,該值為類別數(shù)+1?
? }?
}?
3、 py-faster-rcnn/models/pascal_voc/VGG16/faster_rcnn_alt_opt/stage2_fast_rcnn_train.pt
?
layer {?
? name: 'data'?
? type: 'Python'?
? top: 'data'?
? top: 'rois'?
? top: 'labels'?
? top: 'bbox_targets'?
? top: 'bbox_inside_weights'?
? top: 'bbox_outside_weights'?
? python_param {?
??? module: 'roi_data_layer.layer'?
??? layer: 'RoIDataLayer'?
??? param_str: "'num_classes': 5" #按訓(xùn)練集類別改,該值為類別數(shù)+1?
? }?
}?
?
layer {?
? name: "cls_score"?
? type: "InnerProduct"?
? bottom: "fc7"?
? top: "cls_score"?
? param {
? lr_mult: 1.0
? }?
? param {
? lr_mult: 2.0
? }?
? inner_product_param {?
??? num_output: 5 #按訓(xùn)練集類別改,該值為類別數(shù)+1?
??? weight_filler {?
????? type: "gaussian"?
????? std: 0.01?
??? }?
??? bias_filler {?
????? type: "constant"?
????? value: 0?
??? }?
? }?
}?
?
layer {?
? name: "bbox_pred"?
? type: "InnerProduct"?
? bottom: "fc7"?
? top: "bbox_pred"?
? param {
? lr_mult: 1.0
? }?
? param {
? lr_mult: 2.0
? }?
? inner_product_param {?
??? num_output: 20 #按訓(xùn)練集類別改,該值為(類別數(shù)+1)*4,四個頂點(diǎn)坐標(biāo)?
??? weight_filler {?
????? type: "gaussian"?
????? std: 0.001?
??? }?
??? bias_filler {?
????? type: "constant"?
????? value: 0?
??? }?
? }?
}?
4 、py-faster-rcnn/models/pascal_voc/VGG16/faster_rcnn_alt_opt/stage2_rpn_train.pt
?
layer {?
? name: 'input-data'?
? type: 'Python'?
? top: 'data'?
? top: 'im_info'?
? top: 'gt_boxes'?
? python_param {?
??? module: 'roi_data_layer.layer'?
??? layer: 'RoIDataLayer'?
??? param_str: "'num_classes': 5" #按訓(xùn)練集類別改,該值為類別數(shù)+1?
? }?
}?
5 、py-faster-rcnn/models/pascal_voc/VGG16/faster_rcnn_alt_opt/faster_rcnn_test.pt
?
layer {
? name: "cls_score"
? type: "InnerProduct"
? bottom: "fc7"
? top: "cls_score"
? inner_product_param {
??? num_output: 5#按訓(xùn)練集類別改,該值為類別數(shù)+1
? }
}
layer {
? name: "bbox_pred"
? type: "InnerProduct"
? bottom: "fc7"
? top: "bbox_pred"
? inner_product_param {
??? num_output: 20#按訓(xùn)練集類別改,該值為(類別數(shù)+1)*4
? }
}
6、 py-faster-rcnn/lib/datasets/pascal_voc.py
?
class pascal_voc(imdb):?
??? def __init__(self, image_set, year, devkit_path=None):?
??????? imdb.__init__(self, 'voc_' + year + '_' + image_set)?
??????? self._year = year?
??????? self._image_set = image_set?
??????? self._devkit_path = self._get_default_path() if devkit_path is None \?
??????????????????????????? else devkit_path?
??????? self._data_path = os.path.join(self._devkit_path, 'VOC' + self._year)?
??????? self._classes = ('__background__', # always index 0?
???????????????????????? captcha' # 有幾個類別此處就寫幾個,我是兩個
????????????????????? )?
line 212
?
cls = self._class_to_ind[obj.find('name').text.lower().strip()]?
?
如果你的標(biāo)簽含有大寫字母,可能會出現(xiàn)KeyError的錯誤,所以建議全部使用小寫字母
?
到此代碼修改就搞定了
?
訓(xùn)練
?
訓(xùn)練前還需要注意幾個地方
?
1 cache問題
?
假如你之前訓(xùn)練了官方的VOC2007的數(shù)據(jù)集或其他的數(shù)據(jù)集,是會產(chǎn)生cache的問題的,建議在重新訓(xùn)練新的數(shù)據(jù)之前將其刪除
?
(1) py-faster-rcnn/output
(2) py-faster-rcnn/data/cache
?
2 訓(xùn)練參數(shù)
?
py-faster-rcnn/models/pascal_voc/VGG16/faster_rcnn_alt_opt/stage_fast_rcnn_solver*.pt
?
base_lr: 0.001
lr_policy: 'step'
step_size: 30000
display: 20
....
迭代次數(shù)在文件py-faster-rcnn/tools/train_faster_rcnn_alt_opt.py中進(jìn)行修改
?
line 80
?
max_iters = [80000, 40000, 80000, 40000]
分別對應(yīng)rpn第1階段,fast rcnn第1階段,rpn第2階段,fast rcnn第2階段的迭代次數(shù),自己修改即可,不過注意這里的值不要小于上面的solver里面的step_size的大小,大家自己修改吧
?
開始訓(xùn)練:
?
cd py-faster-rcnn
./experiments/scripts/faster_rcnn_alt_opt.sh 0 VGG16 pascal_voc
?
指明使用第一塊GPU(0),模型是VGG16,訓(xùn)練數(shù)據(jù)是pascal_voc(voc2007),沒問題的話應(yīng)該可以迭代訓(xùn)練了
?
結(jié)果
?
訓(xùn)練完畢,得到我們的訓(xùn)練模型,我們就可以使用它來進(jìn)行我們的object detection了,具體是:
1 將py-faster-rcnn/output/faster_rcnn_alt_opt/voc_2007_trainval/VGG16_faster_rcnn_final.caffemodel,拷貝到py-faster-rcnn/data/faster_rcnn_models下
?
2 將你需要進(jìn)行test的images放在py-faster-rcnn/data/demo下
?
3 修改py-faster-rcnn/tools/demo.py文件
?
CLASSES = ('_background_', 'captcha') #參考你自己的類別寫
?
NETS = {'vgg16': ('VGG16',
'VGG16_faster_rcnn_final.caffemodel'), #改成你訓(xùn)練得到的model的name
'zf': ('ZF',
'ZF_faster_rcnn_final.caffemodel')
}
im_names = ['1559.jpg','1564.jpg']? # 改成自己的test image的name
上幾張我的檢測結(jié)果吧
?? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ? ?
總結(jié)
以上是生活随笔為你收集整理的caffe框架下目标检测——faster-rcnn实战篇操作的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: Faster RCNN解析
- 下一篇: caffe框架下目标检测——faster