關於YOLOv3對VOC型別資料集的mAP計算與PR曲線的繪製 windows和linux均適用
前言
本文所做的工作均建立在已經已經用darknet訓練好自己的模型的基礎上的,不提供與YOLO訓練有關的東西(因為別人已經發夠多了)。儘量寫得傻瓜一些,保持一步一次截圖,因為能看這種部落格的基本都沒啥程式設計師基礎的,連指令碼都沒聽說的菜鳥,只是單純跑跑發個水文的,所以多圖和囉嗦警告,(圖中有些路徑打上馬賽克了,沒有影響)。
1 執行darknet官方程式碼中的detector valid指令,生成對測試集的檢測結果。
.\darknet detector valid <voc.data檔案路徑> <cfg檔案路徑> <weights檔案路徑> -out ""
上面寫的通用格式(請不要直接複製貼上執行,將<>裡的內容替換為自己需要的路徑,其中"<>"不需要,只是用來分隔的!還有windows和linux下檔案路徑的格式不同,並且每個引數之間都需要空格間隔)。(windows通過開啟cmd或者power shell來輸入指令,linux通過ctrl+shift+t開啟終端來輸入指令,要記住輸入指令時你需要通過cd來定位到當前需要執行程式的目錄裡)
voc.data和cfg檔案就是你當時訓練用的配置檔案,weights檔案就是你訓練出來的結果,其中需要修改的是voc.data檔案,其中應該是有五行的,其中第三行是valid就是需要驗證測試集的路徑,其指向的txt檔案格式與第二行train一致(已經訓練過的應該知道是啥了),這裡需要修改成你需要的,畫風如下。
執行完之後應該會在程式的當前目錄生產一個results資料夾,裡面存有檢測結果,檔名為comp4_det_test_<你檢測的類名>.txt,畫風如下所示。
左邊是執行valid指令的過程,右邊是生產的txt檔案,其中txt中資料格式為: 檔名 置信度 x y w h。
2 下載檢測用指令碼檔案 reval_voc_py.py和voc_eval_py.py
(因為沒在CSDN裡面找到新增附件的功能,所以這裡只能放個傳送門了,而且需求積分最低都要1分,所以我也不能改成0分免費給你們。)
windows下python安裝請百度,anaconda就可以了;linux預設就有安裝的,不過是預設的Python2版本的。
如果遇到缺少庫的,請開啟一下python檔案,看看開頭那裡有哪些,一般不會少的,都是些基本的庫。
3 使用reval_voc_py.py計算出mAP值並且生成pkl檔案
python reval_voc_py3.py --voc_dir <voc檔案路徑> --year <年份> --image_set <驗證集檔名> --classes <類名檔案路徑> <輸出資料夾名>
先將第一部生成的results資料夾移動到當前指令碼檔案所在的位置,然後執行上述指令。
首先python表示執行python程式碼
reval_voc_py3.py表示當前執行的指令碼檔名,python3的話就用這個,python2的話用reval_voc.py。
voc檔案路徑就是當時訓練用的VOC資料集的路徑,比如windows下 d:\darknet\scripts\VOCdevkit,linux就是 \home\xxx\darknet\scripts\VOCdevkit,這裡只是打個比方,讀者請替換成自己需要的路徑
年份就是VOC資料集裡VOC檔名裡的時間,比如2007、2012這樣的。
驗證集檔名一般是VOCdevkit\VOC2017\ImageSets\Main中的檔案中txt檔名,比如train.txt,把需要測試的圖片名全部塞進去就可以了,如果沒有的話自行建立(不過沒有的話怎麼訓練的呢)。注意:這裡只需要填檔名,txt字尾都不需要的。
類名檔案路徑就是voc.names檔案的路徑,在voc.data檔案裡面是有的,第4行names那裡。
輸出資料夾名就自己隨便寫了,比如我這裡寫的testForCsdn。
引數全部替換好就可以跑了,大概畫風如下所示:
這時會在腳本當前目錄生成一個存放了pkl檔案的資料夾,名字就是剛才輸入的輸出資料夾名。(這裡的名字不需要和我的一樣,如果你有多個類的話,就會生成多個檔案,檔名就是你的類名)
注意,這時已經能看到mAP值了。(我這裡的驗證集較小,目標較簡單,所以mAP大了些,不用在意)
4 用matplotlib繪製PR曲線
在得到pkl檔案目錄裡直接建立一個python檔案,比如PR_draw.py,內容如下,記得把第三行裡的引數修改一下。
import _pickle as cPickle
import matplotlib.pyplot as plt
fr = open('apple_pr.pkl','rb')#這裡open中第一個引數需要修改成自己生產的pkl檔案
inf = cPickle.load(fr)
fr.close()
x=inf['rec']
y=inf['prec']
plt.figure()
plt.xlabel('recall')
plt.ylabel('precision')
plt.title('PR cruve')
plt.plot(x,y)
plt.show()
print('AP:',inf['ap'])
然後直接執行
python PR_draw.py
最後結果就出來了,噹噹噹當,畫風如下所示:
Ps:目前就寫這麼多了,應該沒啥問題,自我感覺已經夠傻瓜了,有問題請私信我再修改。