CNNを用いた物体検出アルゴリズムの性能比較

# 導入

物体検出アルゴリズムを用いたかった為、現在までに提案されている手法を勉強しようと思ったのですが、思いの他多く何を用いればいいのかわかりませんでした。論文内で精度の比較もされているのですが、結局自分の問題に何を使えばいいんじゃってなった為、調べた限りのアルゴリズム間の性能比較を行ってみました。

物体検出アルゴリズムとは、以下の図のように、画像内の指定された物体の位置 (localization) と分類の確率 (confidence) を出力するアルゴリズムを指します。

![test_dssd.png](https://qiita-image-store.s3.amazonaws.com/0/137574/9039c483-1e8e-f434-8cb8-a7222634a9de.png)


ここでは、物体検出アルゴリズムの中でもCNN (Convolutional Neural Network) を用いたもののみを対象としています。


# 物体検出分野における背景


物体検出 (Object Detection) は画像認識タスクの中の一つで、一般的に画像認識のタスクは以下のように大きく3つに分類されます。

* Classification : 各画像ごとにラベルの分類
* Object Detection : 画像内で検出された各物体領域ごとにラベルの分類
* Segmentation : 画像内の各pixelごとにラベルの分類 (Semantic or Instance)

各タスクごとに用いられるデータセットや指標、そしてアルゴリズムはまったく異なります。なので、まずは物体検出の分野における背景についてまとめました。

## データセット

精度の比較によく用いられているデータセットは [PASCAL VOC2007](http://host.robots.ox.ac.uk/pascal/VOC/voc2007/) と [PASCAL VOC2012](http://host.robots.ox.ac.uk/pascal/VOC/voc2012/) みたいで、どの論文でもこれらのデータセットを用いたベンチマークを示しています。
他にも論文によっては、別の年度の PASCAL VOC や [COCO](http://mscoco.org/) など別のデータセットも使ってたりします。自分たちのアルゴリズムが一番性能良く示せるデータセットを見つけるのも大変そうですね。
PASCAL VOC2007 および 2012 は、共通した全20クラスのカテゴリに bounding box の座標と共にxml形式でアノテーションされています。
クラスは以下の通り。

* Person: person
* Animal: bird, cat, cow, dog, horse, sheep
* Vehicle: aeroplane, bicycle, boat, bus, car, motorbike, train
* Indoor: bottle, chair, dining table, potted plant, sofa, tv/monitor

データセットの一部を見せると以下のようになっています。


VOC 2007 : 000001.jpg
![000001.jpg](https://qiita-image-store.s3.amazonaws.com/0/137574/289d765f-7ec8-d2db-3e88-a144f9eeb22d.jpeg "VOC 2007 : 000001.jpg")

VOC 2007 : 000001.xml

```
<annotation>
	<folder>VOC2007</folder>
	<filename>000001.jpg</filename>
	<source>
		<database>The VOC2007 Database</database>
		<annotation>PASCAL VOC2007</annotation>
		<image>flickr</image>
		<flickrid>341012865</flickrid>
	</source>
	<owner>
		<flickrid>Fried Camels</flickrid>
		<name>Jinky the Fruit Bat</name>
	</owner>
	<size>
		<width>353</width>
		<height>500</height>
		<depth>3</depth>
	</size>
	<segmented>0</segmented>
	<object>
		<name>dog</name>
		<pose>Left</pose>
		<truncated>1</truncated>
		<difficult>0</difficult>
		<bndbox>
			<xmin>48</xmin>
			<ymin>240</ymin>
			<xmax>195</xmax>
			<ymax>371</ymax>
		</bndbox>
	</object>
	<object>
		<name>person</name>
		<pose>Left</pose>
		<truncated>1</truncated>
		<difficult>0</difficult>
		<bndbox>
			<xmin>8</xmin>
			<ymin>12</ymin>
			<xmax>352</xmax>
			<ymax>498</ymax>
		</bndbox>
	</object>
</annotation>
```

画像のアノテーションとして、ラベル名 (dog, person) と bounding boxの各頂点の座標 (xmin, ymin, xmax, ymax) が記されています。
その他にも、画像の情報だったり、物体検出以外のコンペで使われる情報だったりが記されています。Segmentation の分野でもこれらのデータセットは有名です。


## 指標

物体検出の分野で重要とされている指標は、**mAP (mean Average Precision)** と **FPS (Frame Per Second)** みたいです。つまり物体検出精度と処理速度ということですね。

~~Precision は偽陽性率を測る指標であることから、検出された物体がどれだけあっているかに注目しているようです。つまり誤検出が如何に少ないかということで競っているみたいですね。検出されない物体はほとんどないということなんですかね。 AP (Average Precision) はカテゴリごとの平均 Precision を示しており、これの全平均が mAP となります。~~
AP (Average Precision) は Precision-Recall curve の下面積 (AUC) を意味している[^ap]みたいです。つまり Precision と Recall を平等に評価している指標が AP だということです。そして各クラスごとの AP を平均したのが mAP ということです。

以下のように論文内の table[^6] には各ラベルごとのAPも示されていますが、読んでてしんどいです。。

![ssd_result.png](https://qiita-image-store.s3.amazonaws.com/0/137574/e6c25bbf-f985-2bb7-d76a-face638d7ebc.png)

処理速度もこの分野では重要で、精度はもちろん Real-Time に検出できるかどうかも評価のポイントみたいです。YOLO [^5] 内では 21 FPS でも Real-Time ではないといっているので、なかなか厳しいですね。21 FPS  もあれば結構ヌルヌルだと思うんですが。


## アルゴリズム

物体検出アルゴリズムについてです。

ここ数年におけるCNNを用いた物体検出アルゴリズムの進歩は、他の分野と比較しても突出している気がします。新しいアルゴリズムが提案されるたびに、すぐその問題点を克服した手法が提案されています。

物体検出アルゴリズムは以下の図にある通り、Region Proposal, Classification, Bounding Box Regression の 3 phase に大きく別れています。

![fig.002.jpeg](https://qiita-image-store.s3.amazonaws.com/0/137574/f9b392b5-462d-59ee-08e7-b8e352e008c3.jpeg)

① Region Proposal : 物体らしい箇所を検出
② Classification : 検出箇所のラベル分類
③ Bounding Box Regression : 正確な物体を囲う位置座標を回帰

このアルゴリズムを説明のベースに、提案された中でも引用数の多い手法の特徴、問題点を時系列順に列挙してみました。

|model|Pros|Cons|
|:--|:--|:--|
|R-CNN[^1] (CVPR2014)|(① によって得られた領域から特徴抽出する為に) CNNを用いた物体検出アルゴリズムのベースを提案|物体領域候補の重複による計算の冗長性 / ① には既存手法[^9]、② ③ にはSVMを用いている / Ad hoc training objectives (② ③ の学習および CNN の fine-tune を個別に行う必要がある)|
|SPPnet[^2] (ECCV2014)|spatial pyramid pooling layer の提案によってR-CNNにおける計算の冗長性を解消| ベースがR-CNNなので学習が ad hoc なのは変わらず|
|Fast R-CNN[^3] (ICCV2015)|② と ③ を同時に学習する multi-task learning を用いた手法の提案 (ad hoc な学習からの脱却)|① は既存手法を用いているため、冗長な検出が多い|
|Faster R-CNN[^4] (NIPS2015)|① もCNNで行うことで End to End な学習を可能とする手法の提案|これまでの手法より高速だが Real-Time な検出が行えない (5 FPS)|
|YOLO[^5] (CVPR2015)|画像をグリッドに分割して各領域ごとに ② ③ を行う別アプローチを提案  ( ① の排除) / 1つのシンプルなネットワークで構築 / 45-155 FPS での Real-Time な検出速度を達成|アルゴリズムの制約上、画像内に多オブジェクトがある場合の検出は困難 |
|SSD[^6] (ECCV2016)|YOLOと同じく ① を排除したシンプルなネットワークによる手法の提案 / 多オブジェクトの検出に比較的強くYOLOより高速|恣意的なパラメータがまだ多い (Choosing scales and aspect ratios for default boxes, Hard negative mining, Data augmentation)|
|YOLOv2[^7] (arXiv2016)|ResNet と SSD を組み合わせた手法より高い精度を達成 / 背景の誤検出が少ない (Recallが高い) / Batch Normalization を追加 |YOLOベースなため相変わらず多オブジェクト検出に弱い |
|DSSD[^8] (arXiv2017)|SSD の fine-tune に VGG ではなく (Batch Normalizationを適用させた) Residual-101 を用い、Deconvolution layer を追加することで検出精度を向上させた|Deconvolution layer を追加したことで速度は SSD より劣っている|


この表を埋める際に、[ここ](http://tech-blog.abeja.asia/entry/object-detection-summary)を参考にさせていただきました。
これを見る限り、使うのはYOLO系かSSD系がいいですかね。

補足として、ICCV 2017で発表された Mask R-CNN[^10] は、 Fast, Faster R-CNN などで用いられている Region Proposal の領域を ROI Pooling する手法を改善し、セグメンテーションなどのより難易度の高いタスクに用いられているみたいです。
YOLOやSSDとは比較されていないので今回は対象に含んでいませんが、参考までに。

# モデル性能比較

いよいよ本題のモデル間の性能比較になります。

学習および評価したデータセットが同じでないと比較しにくいため、今回は以下の2パターンで比較を行いました。処理速度は全て同様の GPU (Titan X) 上で行っている結果のみ拾ってきているので、ほぼ平等に評価できていると思います。
また、R-CNNとSPPnetに関してはあまり比較されているデータがなかったので今回は外しました。

**train : VOC 2007 + 2012, test : VOC 2007**

|model|mAP|FPS|
|:--|:--|:--|
|Fast R-CNN[^3]|70.0|0.5|
|Faster R-CNN[^4]|73.2|7|
|YOLO[^5]|63.4|45|
|Fast YOLO[^5]|52.7|155|
|SSD (300)[^6]|74.3|46|
|SSD (512)[^6]|76.8|19|
|YOLOv2 (416)[^7]|76.8|67|
|YOLOv2 (544)[^7]|78.6|40|
|DSSD[^8]|81.5|6.6|

**train : VOC 2007 + 2012, test : VOC 2012**

|model|mAP|
|:--|:--|
|Fast R-CNN[^3]|68.4|
|Faster R-CNN[^4]|70.4|
|YOLO[^5]|57.9|
|SSD (300)[^6]|72.4|
|SSD (512)[^6]|74.9|
|YOLOv2 (544)[^7]|73.4|
|DSSD[^8]|80.0|

結果を見るとYOLO系とSSD系の一騎打ちです。
やはり精度と速度はトレードオフな関係で、各アルゴリズムは結局モデルに入力する画像の解像度を変えたりすることで最高のパフォーマンスを示そうとしているみたいですね。
この結果とアルゴリズムの特性を考えて、自分の問題に適したmodelを選択するのが良さそうです。

# 結論

自分が調べた限りでは DSSD が最も高い精度となりましたが、速度とのバランスを考えると YOLOv2 が最高のパフォーマンスを示しているみたいです。
ただアルゴリズムの性質を考えると、多オブジェクト検出に関してはSSD系を用いた方が良い結果を示しそうです。
どちらのモデルもシンプルなので構築しやすいと思いますが、多オブジェクト問題に取り組むということもあって自分はまずSSD系のアルゴリズムを用いてみようかなと考えています。特にReal-Time検出とかも考えてはいないので。

以下にSSDやYOLOを各フレームワークで実装している方々を紹介しておきます。

SSD系

* [TensorFlow 1](https://github.com/balancap/SSD-Tensorflow)
* [TensorFlow 2](https://github.com/georgesung/ssd_tensorflow_traffic_sign_detection)
* [Keras 1](https://github.com/rykov8/ssd_keras)
* [Keras 2](https://github.com/pierluigiferrari/ssd_keras)
* [Chainer 1](https://github.com/Hakuyume/chainer-ssd)
* [Chainer 2](https://github.com/ninhydrin/chainer-SSD)
* [PyTorch 1](https://github.com/amdegroot/ssd.pytorch)
* [PyTorch 2](https://github.com/kuangliu/pytorch-ssd)

YOLO系

* [TensorFlow 1](https://github.com/thtrieu/darkflow)
* [TensorFlow 2](https://github.com/nilboy/tensorflow-yolo)
* [Keras 1](https://github.com/allanzelener/YAD2K)
* [Keras 2](https://github.com/experiencor/basic-yolo-keras)
* [Chainer 1](https://github.com/leetenki/YOLOv2)
* [Chainer 2](https://github.com/ashitani/YOLO_chainer)
* [PyTorch 1](https://github.com/longcw/yolo2-pytorch)
* [PyTorch 2](https://github.com/marvis/pytorch-yolo2)

PyTorch めっちゃ多い、、いつの間にこんな勢力増してたんだ、、

# References

[^1]: [Girshick, Ross, et al. "Rich feature hierarchies for accurate object detection and semantic segmentation." Proceedings of the IEEE conference on computer vision and pattern recognition. (2014)](https://www.cv-foundation.org/openaccess/content_cvpr_2014/html/Girshick_Rich_Feature_Hierarchies_2014_CVPR_paper.html)
[^2]: [He, Kaiming, et al. "Spatial pyramid pooling in deep convolutional networks for visual recognition." IEEE transactions on pattern analysis and machine intelligence 37.9 (2015): 1904-1916.](http://ieeexplore.ieee.org/abstract/document/7005506/) / [arXiv](https://arxiv.org/abs/1406.4729)
[^3]: [Girshick, Ross. "Fast r-cnn." Proceedings of the IEEE international conference on computer vision. (2015)](https://www.cv-foundation.org/openaccess/content_iccv_2015/html/Girshick_Fast_R-CNN_ICCV_2015_paper.html)
[^4]: [Ren, Shaoqing, et al. "Faster R-CNN: Towards real-time object detection with region proposal networks." Advances in neural information processing systems. (2015)](http://papers.nips.cc/paper/5638-faster-r-cnn-towards-real-time-object-detection-with-region-proposal-networks)
[^5]: [Redmon, Joseph, et al. "You only look once: Unified, real-time object detection." Proceedings of the IEEE Conference on Computer Vision and Pattern Recognition. (2016)](https://www.cv-foundation.org/openaccess/content_cvpr_2016/html/Redmon_You_Only_Look_CVPR_2016_paper.html) / [arXiv](https://arxiv.org/abs/1506.02640)
[^6]: [Liu, Wei, et al. "Ssd: Single shot multibox detector." European conference on computer vision. Springer, Cham, (2016)](https://link.springer.com/chapter/10.1007%2F978-3-319-46448-0_2) / [arXiv](https://arxiv.org/abs/1512.02325)
[^7]: [Redmon, Joseph, and Ali Farhadi. "YOLO9000: better, faster, stronger." arXiv preprint arXiv:1612.08242 (2016)](https://arxiv.org/abs/1612.08242)
[^8]: [Fu, Cheng-Yang, et al. "DSSD: Deconvolutional Single Shot Detector." arXiv preprint arXiv:1701.06659 (2017)](https://arxiv.org/abs/1701.06659)
[^9]: [Uijlings, Jasper RR, et al. "Selective search for object recognition." International journal of computer vision 104.2 (2013): 154-171.](https://link.springer.com/article/10.1007/s11263-013-0620-5)
[^10]: [He, Kaiming, et al. "Mask r-cnn." arXiv preprint arXiv:1703.06870 (2017)](https://arxiv.org/abs/1703.06870)
[^ap]: Average Precision と AUC of Precision-Recall curve の計算のされ方はライブラリの実装によっては[異なる場合](https://stats.stackexchange.com/questions/157012/area-under-precision-recall-curve-auc-of-pr-curve-and-average-precision-ap)がある。