単一ステージ検出器をRPNとして使用する¶
領域提案ネットワーク (RPN) は、Faster R-CNN のサブモジュールであり、Faster R-CNN の第2ステージの提案を生成します。MMDetection のほとんどの2ステージ検出器は、RPNHead
を使用してRPNとして提案を生成します。ただし、単一ステージ検出器は、そのバウンディングボックスの予測も領域の提案と見なすことができ、R-CNN で絞り込むことができるため、RPN として機能できます。したがって、MMDetection v3.0 はそれをサポートしています。
プロセス全体を説明するために、ここでは、アンカーフリーの単一ステージモデル FCOS を Faster R-CNN で RPN として使用する方法の例を示します。
このチュートリアルの概要は次のとおりです
Faster R-CNN で
FCOSHead
をRPNHead
として使用する提案を評価する
事前トレーニング済み FCOS を使用してカスタマイズされた Faster R-CNN をトレーニングする
Faster R-CNN で FCOSHead
を RPNHead
として使用する¶
Faster R-CNN で FCOSHead
を RPNHead
として設定するには、configs/faster_rcnn/faster-rcnn_r50_fpn_fcos-rpn_1x_coco.py
という名前の新しい設定ファイルを作成し、rpn_head
の設定を configs/fcos/fcos_r50-caffe_fpn_gn-head_1x_coco.py
の bbox_head
の設定に置き換える必要があります。また、ストライドが [8, 16, 32, 64, 128]
の FCOS のネック設定を引き続き使用し、bbox_roi_extractor
の featmap_strides
を [8, 16, 32, 64, 128]
に更新します。損失が NAN になるのを防ぐため、最初の 500 イテレーションではなく、最初の 1000 イテレーションでウォームアップを適用します。つまり、学習率はよりゆっくりと増加します。設定は次のとおりです
_base_ = [
'../_base_/models/faster-rcnn_r50_fpn.py',
'../_base_/datasets/coco_detection.py',
'../_base_/schedules/schedule_1x.py', '../_base_/default_runtime.py'
]
model = dict(
# copied from configs/fcos/fcos_r50-caffe_fpn_gn-head_1x_coco.py
neck=dict(
start_level=1,
add_extra_convs='on_output', # use P5
relu_before_extra_convs=True),
rpn_head=dict(
_delete_=True, # ignore the unused old settings
type='FCOSHead',
num_classes=1, # num_classes = 1 for rpn, if num_classes > 1, it will be set to 1 in TwoStageDetector automatically
in_channels=256,
stacked_convs=4,
feat_channels=256,
strides=[8, 16, 32, 64, 128],
loss_cls=dict(
type='FocalLoss',
use_sigmoid=True,
gamma=2.0,
alpha=0.25,
loss_weight=1.0),
loss_bbox=dict(type='IoULoss', loss_weight=1.0),
loss_centerness=dict(
type='CrossEntropyLoss', use_sigmoid=True, loss_weight=1.0)),
roi_head=dict( # update featmap_strides due to the strides in neck
bbox_roi_extractor=dict(featmap_strides=[8, 16, 32, 64, 128])))
# learning rate
param_scheduler = [
dict(
type='LinearLR', start_factor=0.001, by_epoch=False, begin=0,
end=1000), # Slowly increase lr, otherwise loss becomes NAN
dict(
type='MultiStepLR',
begin=0,
end=12,
by_epoch=True,
milestones=[8, 11],
gamma=0.1)
]
次に、次のコマンドを使用して、カスタマイズしたモデルをトレーニングできます。トレーニングコマンドの詳細については、こちら を参照してください。
# training with 8 GPUS
bash tools/dist_train.sh configs/faster_rcnn/faster-rcnn_r50_fpn_fcos-rpn_1x_coco.py \
8 \
--work-dir ./work_dirs/faster-rcnn_r50_fpn_fcos-rpn_1x_coco
提案を評価する¶
提案の質は検出器の性能に大きく影響するため、提案を評価する方法も提供しています。上記と同様に、configs/rpn/fcos-rpn_r50_fpn_1x_coco.py
という名前の新しい設定ファイルを作成し、rpn_head
の設定を configs/fcos/fcos_r50-caffe_fpn_gn-head_1x_coco.py
の bbox_head
の設定に置き換えます。
_base_ = [
'../_base_/models/rpn_r50_fpn.py', '../_base_/datasets/coco_detection.py',
'../_base_/schedules/schedule_1x.py', '../_base_/default_runtime.py'
]
val_evaluator = dict(metric='proposal_fast')
test_evaluator = val_evaluator
model = dict(
# copied from configs/fcos/fcos_r50-caffe_fpn_gn-head_1x_coco.py
neck=dict(
start_level=1,
add_extra_convs='on_output', # use P5
relu_before_extra_convs=True),
rpn_head=dict(
_delete_=True, # ignore the unused old settings
type='FCOSHead',
num_classes=1, # num_classes = 1 for rpn, if num_classes > 1, it will be set to 1 in RPN automatically
in_channels=256,
stacked_convs=4,
feat_channels=256,
strides=[8, 16, 32, 64, 128],
loss_cls=dict(
type='FocalLoss',
use_sigmoid=True,
gamma=2.0,
alpha=0.25,
loss_weight=1.0),
loss_bbox=dict(type='IoULoss', loss_weight=1.0),
loss_centerness=dict(
type='CrossEntropyLoss', use_sigmoid=True, loss_weight=1.0)))
トレーニング後にチェックポイント ./work_dirs/faster-rcnn_r50_fpn_fcos-rpn_1x_coco/epoch_12.pth
があるとします。次のコマンドで提案の質を評価できます。
# testing with 8 GPUs
bash tools/dist_test.sh \
configs/rpn/fcos-rpn_r50_fpn_1x_coco.py \
./work_dirs/faster-rcnn_r50_fpn_fcos-rpn_1x_coco/epoch_12.pth \
8
事前トレーニング済み FCOS を使用してカスタマイズされた Faster R-CNN をトレーニングする¶
事前トレーニングは、トレーニングの収束を高速化するだけでなく、検出器の性能も向上させます。したがって、ここでは、事前トレーニング済み FCOS を RPN として使用してトレーニングを高速化し、精度を向上させる方法の例を示します。 FCOSHead
を Faster R-CNN の rpn ヘッドとして使用し、事前トレーニング済み fcos_r50-caffe_fpn_gn-head_1x_coco
でトレーニングするとします。 configs/faster_rcnn/faster-rcnn_r50-caffe_fpn_fcos-rpn_1x_coco.py
という名前の設定ファイルの内容は次のとおりです。 fcos_r50-caffe_fpn_gn-head_1x_coco
は caffe バージョンの ResNet50 を使用しているため、data_preprocessor
のピクセル平均と標準偏差を更新する必要があることに注意してください。
_base_ = [
'../_base_/models/faster-rcnn_r50_fpn.py',
'../_base_/datasets/coco_detection.py',
'../_base_/schedules/schedule_1x.py', '../_base_/default_runtime.py'
]
model = dict(
data_preprocessor=dict(
mean=[103.530, 116.280, 123.675],
std=[1.0, 1.0, 1.0],
bgr_to_rgb=False),
backbone=dict(
norm_cfg=dict(type='BN', requires_grad=False),
style='caffe',
init_cfg=None), # the checkpoint in ``load_from`` contains the weights of backbone
neck=dict(
start_level=1,
add_extra_convs='on_output', # use P5
relu_before_extra_convs=True),
rpn_head=dict(
_delete_=True, # ignore the unused old settings
type='FCOSHead',
num_classes=1, # num_classes = 1 for rpn, if num_classes > 1, it will be set to 1 in TwoStageDetector automatically
in_channels=256,
stacked_convs=4,
feat_channels=256,
strides=[8, 16, 32, 64, 128],
loss_cls=dict(
type='FocalLoss',
use_sigmoid=True,
gamma=2.0,
alpha=0.25,
loss_weight=1.0),
loss_bbox=dict(type='IoULoss', loss_weight=1.0),
loss_centerness=dict(
type='CrossEntropyLoss', use_sigmoid=True, loss_weight=1.0)),
roi_head=dict( # update featmap_strides due to the strides in neck
bbox_roi_extractor=dict(featmap_strides=[8, 16, 32, 64, 128])))
load_from = 'https://download.openmmlab.com/mmdetection/v2.0/fcos/fcos_r50_caffe_fpn_gn-head_1x_coco/fcos_r50_caffe_fpn_gn-head_1x_coco-821213aa.pth'
トレーニングのコマンドは次のとおりです。
bash tools/dist_train.sh \
configs/faster_rcnn/faster-rcnn_r50-caffe_fpn_fcos-rpn_1x_coco.py \
8 \
--work-dir ./work_dirs/faster-rcnn_r50-caffe_fpn_fcos-rpn_1x_coco