rkdora's Blog

画像認識による洗濯表示の識別

洗濯表示しらべくん

画像から洗濯表示を識別し、意味を表示するWEBアプリケーション。
CNNによりモデルを作成し、FlaskでWEBアプリ化、Herokuにデプロイしてある。

洗濯表示しらべくん

TOP画面 f:id:rkdora:20190917204104p:plain

予測結果表示画面 f:id:rkdora:20190917204120p:plain

洗濯表示とは?
衣服についたタグのマークのこと。 洗濯や乾燥の方法、アイロンのかけ方やクリーニングの方法などが示されている。 全41種類。世界共通。

f:id:rkdora:20190917204845p:plain
洗濯表示一覧

デモ動画

youtu.be

HAIT Lab 福岡にて、Best Product Awardを受賞。

ソースコード

GitHub - HAIT-Lab-Fukuoka-TeamC/care-label-app: 洗濯表示しらべくん

開発期間

2019/09/09 ~ 09/16

開発の流れ

  1. 洗濯表示41種類、約200枚を集める
  2. 約30万枚(30GB弱)に水増し (明るさ、ノイズ、回転、移動)
  3. CNNを用いてモデルを作成し、重みを保存
  4. FlaskでWebアプリ化
  5. Herokuにデプロイ

1. 洗濯表示41種類、約200枚を集める

洗濯タグを撮影→トリミング→該当するフォルダに仕分け。
珍しい洗濯表示などは、ネットから集めた。

https://github.com/HAIT-Lab-Fukuoka-TeamC/care-label-app/tree/master/pre-all/train-seeds

2. 約30万枚(30GB弱)に水増し

1枚の画像から1500枚弱に水増しする。
DeepLearningには大量のデータが必要と聞いていたため、大量に用意することにした。
明るさ、ノイズ、回転、移動(縦横斜め)それぞれを段階的に複合させることで水増しを行う。

水増しにはOpenCVを用いている。
工夫した点
1回のプログラム実行で全ての種画像を水増しできること。
それまでは、1回のプログラム実行で1枚から1500枚に水増しを行なっていた。ただ、これでは200枚の種画像を水増ししようとすると200回プログラムを書き直して実行しなければならない。
そこで、globモジュールを使いファイル・フォルダ名を取得することにより1回のプログラム実行で200枚の種画像をそれぞれ1500枚、計30万枚へと水増しできるようになり、作業効率が大幅に改善した。

つまずいた点
Linux(ノート)とWindows(デスクトップ)で開発を往復することがあり、Windowsでうまく動作しなかった。

Windowsで使う際にはパスを「/」から「¥¥」へと変える必要があることがわかった。

3. CNNを用いてモデルを作成し、重みを保存

画像サイズを50×50に。

f:id:rkdora:20190917213926p:plain
リサイズ前
f:id:rkdora:20190917213928p:plain
リサイズ後

CNNの層の決め方はよくわからなかった。

# CNNを構築
model = Sequential()

model.add(Conv2D(32, (3, 3), padding='same',input_shape=X_train.shape[1:]))
model.add(Activation('relu'))
model.add(Conv2D(32, (3, 3)))
model.add(Activation('relu'))
model.add(MaxPooling2D(pool_size=(2, 2)))
model.add(Dropout(0.25))

model.add(Conv2D(64, (3, 3), padding='same'))
model.add(Activation('relu'))
model.add(Conv2D(64, (3, 3)))
model.add(Activation('relu'))
model.add(MaxPooling2D(pool_size=(2, 2)))
model.add(Dropout(0.25))

model.add(Flatten())
model.add(Dense(512))
model.add(Activation('relu'))
model.add(Dropout(0.5))
model.add(Dense(len(folder)))
model.add(Activation('softmax'))

epoch数は3で訓練し、評価は
[0.011538714563043074, 0.9979025710419486]
trainデータ、testデータ共に99%ほどの精度に。
ただ、この数字は全く参考にならない。
種画像を水増ししたもので評価しているためだ。
体感では、8割程度の精度だと感じている(種画像の数や、似ているものがあるかどうかで結構ばらつく)
f:id:rkdora:20190917215205p:plain

つまずいた点
30万枚という大量のデータを学習させようとすると、長時間かかるためjupyter-notebookでは辛いものがあった。(セッション切れなど)

Google ColaboratoryによりGPUを使うことも試してみたが、そのためにはデータをGoogleドライブにおく必要があった。

30万枚をアップしようとしたものの、長時間かかりエラーを吐かれ断念。

Google Colaboratory上で画像を水増しし、Google Driveに直接出力しようとしたものの、時間がかかりすぎるため断念。

結局、Jupyter NotebookのコードをそのままPythonファイルにしてデスクトップで実行することで解決。1時間程度で学習が終わった。

4. FlaskでWebアプリ化

3で保存したモデルと重みを用い、アップロードされた画像に対して洗濯表示を予測する処理を裏で行う。
Top画面と、結果出力画面の2画面構成。

工夫した点
Top画面には使い方を載せた。

つまずいた点
Flaskにおける画像の表示

解決策は2つ。

  • ルーティング処理(自分はこちらを選択。uploadsフォルダを作り、ルーティング処理をした。app.pyの下の方)
    または
  • staticフォルダ下に画像を配置する

Djangoと比べてとても楽に感じた。
小さい規模のアプリケーションならFlaskの方がお手軽だと思う。

5. Herokuにデプロイ

軽量化させるため、heroku用にリポジトリを分けた。
ソースコードは以下の通り。

GitHub - HAIT-Lab-Fukuoka-TeamC/care-label-heroku

構成は以下の通り。
f:id:rkdora:20190917221006p:plain

and_weight.hdf5、and.jsonは意味なし。

つまずいた点
Herokuにデプロイできない。
requirements.txtでエラーがでた。調べたところ、pyenvによる仮想環境の構築を行なっていなかったことが原因だった。(Anacondaもrequirementsに含まれている状態がいけなかったらしい)
pyenvにより仮想環境の構築をすることで解決。

つまずいた点
Herokuにアップロードした画像を保存できない。
元々は、「画像をアップロード→uploadsフォルダに保存→予測結果表示画面に保存した画像を表示」という構成だった。
ローカルでは、上の構成でうまく動作していたのだがおそらくHerokuの仕様により保存できなかった。
そこで、保存しない構成に変更した。具体的には、画面遷移時にデータを渡す構成にした。

感想

機械学習を用いた初めてのプロダクトになった。Python機械学習OpenCVによる画像処理、FlaskによるWEBアプリ化などわからないことだらけだったが、短期間でなんとか形にすることができてよかった。
画像認識による洗濯表示の識別は、自分が調べた中では過去に例がなかったので思いつくことができてよかった。
今は撮った画像をトリミングしてからアップロードする必要があるが、ゆくゆくは撮った画像をそのままアップロードし、複数の洗濯表示を識別するところまで持っていきたい。

参考記事

KerasのCNNを使用してオリジナル画像で画像認識を行ってみる - AI人工知能テクノロジー

Re:ゼロからFlaskで始めるHeroku生活 〜環境構築とこんにちは世界〜 - Qiita

Flaskで画像予測のWebアプリを作りHerokuにデブロイするまで - Qiita

Pythonでglobモジュールを使う方法【初心者向け】 | TechAcademyマガジン