YOLOv3-tinyで学習してみた3(学習結果を使ってJetson Nanoで動かす)
学習したweightsを使いJetson Nano,DeepstreamでYolov3-tinyを動かして駐車禁止を検出してみます。
13.Jetson Nanoの準備
過去の記事、'Jetson NanoでDeepStreamを使ってYOLOv3-tinyを動かす'を参考にYOLOを動かす環境を構築します。
14.YoloのPlugin変更
Depstream用のYOLO Pluginはソースにハードコーティングしている箇所があるので変更します。基本的にはNvidiaの資料(次のリンク)の通りです。
https://docs.nvidia.com/metropolis/deepstream/Custom_YOLO_Model_in_the_DeepStream_YOLO_App.pdf
1)YOLOのフォルダーを開く
- Nanoの画面の左上の方にあるFileアイコン(ハードディスクの絵)を右クリック、New Windowを選ぶ
- File windowの左下のOther Locationsを選択、画面に表示されるComputerをクリック
- /opt/nvidia/deepstream/deepstream-4.0/sources/objectDetector_Yoloと開いていく。
- objectDetector_Yoloの画面で右クリック、Open in Terminalでこのフォルダで端末が開きます。
2)nvdsparsebbox_Yolo.cppの変更
nvdsparsebbox_Yolo.cppはnvdsinfer_custom_impl_Yoloフォルダにあります。Filesの画面でnvdsparsebbox_Yolo.cppをダブルクリックするとviエディタで開くので、そのまま編集します。
①クラスの数を80→1に変更
/*static const int NUM_CLASSES_YOLO = 80;*/
static const int NUM_CLASSES_YOLO = 1;
②関数NvDsInferParseCustomYoloV3Tiny
MASKを{1,2,3}から{0,1,2}に変更(学習に使ったcfgにあわせる)
extern "C" bool NvDsInferParseCustomYoloV3Tiny(
std::vector<NvDsInferLayerInfo> const& outputLayersInfo,
NvDsInferNetworkInfo const& networkInfo,
NvDsInferParseDetectionParams const& detectionParams,
std::vector<NvDsInferParseObjectInfo>& objectList)
{
static const std::vector<float> kANCHORS = {
10, 14, 23, 27, 37, 58, 81, 82, 135, 169, 344, 319};
static const std::vector<std::vector<int>> kMASKS = {
{3, 4, 5},
{0, 1, 2}}; // as per output result, select {1,2,3}
//{1, 2, 3}}; return NvDsInferParseYoloV3 (
outputLayersInfo, networkInfo, detectionParams, objectList,
kANCHORS, kMASKS);
}
端末のカレントディレクトリ、/opt/nvidia/deepstream/deepstream-4.0/sources/objectDetector_Yoloに移動します。
・CUDAバージョン確認
nvcc -V
・CUDAバージョン設定(10.0の例)
export CUDA_VER=10.0
・make
make -C nvdsinfer_custom_impl_Yolo
15.YOLO cfgファイル、weightファイル他ノアップロード
パソコンで学習に使ったcfgファイルと、学習で作られたweightをJetson Nanoにアップロードします。またクラスの名称を示すobj.namesをlabels_no_parking.txtとファイル名を変えてアップロードします。
またYOLOに入力する動画ファイル(スマホで撮影したもの。test.mp4)も一緒にアップロードします。
- yolov3-tiny_obj2.cfg
- yolov3-tiny_obj2_last.weights
- labels_no_parking.txt
- test.mp4
パソコンからJetson NanoのJupyterLabを開き、ドキュメントフォルダにドラッグ&ドロップするとJetson Nanoにアップロードされます。
Jetson Nanoの
/opt/nvidia/deepstream/deepstream-4.0/sources/objectDetector_Yolo
の下にtestフォルダを作り、全てそこに格納します。
16.DeepStreamの設定ファイルの変更
フォルダobjectDetector_Yoloにある次の2つの設定ファイルをコピー・編集して新たな設定ファイルを作ります。
- deepstream_app_config_yoloV3_tiny.txt
- config_infer_primary_yoloV3_tiny.txt
①deepstream_app_config_yoloV3_tiny_no_parking.txt
変更箇所は次の通りです。
- ファイル名を変更(後ろにno_parkingを追加)してコピーします。
cp deepstream_app_config_yoloV3_tiny.txt deepstream_app_config_yoloV3_tiny_no_parking.txt
- DeepStreamのsourceを駐車禁止の動画ファイルに変更します。
[source0]
enable=1
#Type - 1=CameraV4L2 2=URI 3=MultiURI
type=3
#uri=file://../../samples/streams/sample_1080p_h264.mp4
uri=file://test/test.mp4 - labels,config_infer_primary_yoloV3_tiny.txtの変更
# config-file property is mandatory for any gie section.
# Other properties are optional and if set will override the properties set in
# the infer config file.
[primary-gie]
enable=1
gpu-id=0
#model-engine-file=model_b1_fp32.engine
#labelfile-path=labels.txt
labelfile-path=test/labels_no_parking.txt
batch-size=1
#Required by the app for OSD, not a plugin property
bbox-border-color0=1;0;0;1
bbox-border-color1=0;1;1;1
bbox-border-color2=0;0;1;1
bbox-border-color3=0;1;0;1
gie-unique-id=1
nvbuf-memory-type=0
#config-file=config_infer_primary_yoloV3_tiny.txt
config-file=config_infer_primary_yoloV3_tiny_no_parking.txt
②config_infer_primary_yoloV3_tiny_no_parking.txt
- ファイル名を変更(後ろにno_parkingを追加)してコピーします。
cp config_infer_primary_yoloV3_tiny.txt config_infer_primary_yoloV3_tiny_no_parking.txt
- Yolo cfg,labels,weightファイルの設定を変更
[property]
gpu-id=0
net-scale-factor=1
#0=RGB, 1=BGR
model-color-format=0
#custom-network-config=yolov3-tiny.cfg
custom-network-config=test/yolov3-tiny_obj2.cfg
#model-file=yolov3-tiny.weights
model-file=test/yolov3-tiny_obj2_last.weights#model-engine-file=model_b1_fp32.engine
#labelfile-path=labels.txt
labelfile-path=test/labels_no_parking.txt
フォルダの中身を整理すると、次の通りになります。
- objectDetector_Yoloフォルダ deepstream_app_config_yoloV3_tiny_no_parking.txt
config_infer_primary_yoloV3_tiny_no_parking.txt
- objectDetector_Yolo/testフォルダ
labels_no_parking.txt
test.mp4
yolov3-tiny_obj2.cfg
yolov3-tiny_obj2_last_weights
17.動かしてみる
次のコマンドでサンプルが動きます。動き始めるまでは少し時間がかかります。なぜか画面は横表示でしたが、正常に検出できました。
pキーで一時停止、rキーで再開します。
deepstream-app -c deepstream_app_config_yoloV3_tiny_no_parking.txt
2箇所の動画の検出結果を貼り付けます。左から3枚目は検出できていませんが、ちょっと近づくと検出開始し、看板が少しくらい斜めを向いても検出できていました。
17.まとめ
YOLOのデータ集め(動画撮影)から学習まで試してみました。ブログに書きながらですが、週末2回どっぷりかかりました。
手順さえわかれば、クラス数が1つということもあり、思ったほど大変な作業ではありませんでした。ただし、認識率向上やクラス数を増やすといったことをすると、学習用のパラメータ調整、画像データ作り等々、いろいろチューニングしなきゃならないんだろうなと思います。
github.com
おしまい