質問するログイン新規登録

Q&A

2回答

2908閲覧

マルチラベル分類における重み付けについて教えて下さい

orionza

総合スコア1

Python

Pythonは、コードの読みやすさが特徴的なプログラミング言語の1つです。 強い型付け、動的型付けに対応しており、後方互換性がないバージョン2系とバージョン3系が使用されています。 商用製品の開発にも無料で使用でき、OSだけでなく仮想環境にも対応。Unicodeによる文字列操作をサポートしているため、日本語処理も標準で可能です。

0グッド

0クリップ

投稿2021/05/19 22:59

編集2021/05/21 00:26

0

0

マルチラベル分類での重み付けについてお聞きしたいです。

現在tensorflowにて4種類の画像識別モデルを構築しようと思っています。
画像1枚を入力として受け取り、各クラスの物体がが写っている/いないという
判断(つまり4クラスのアウトプット)をさせています。

しかしデータ数に偏りがあり、ざっくりとした比は1:1:14:14という感じになっているため
データに重みをつけて学習をさせたいのですが、model.fit()のclass_weight引数で重みをつけてみても
イマイチ結果が変わっていないいような気がします。

調べている時、loss関数を(binary_crossentropyではなく)自前で用意するという方法も
あったのですが...今回のケースではそちらのほうが適しているのでしょうか?

以下コードです。
(学習の部分だけ載せていますが、他にも必要なものがあればお知らせください)

python

1 2# 今回のMETRICSで採用 3def macro_f1(y, y_hat, thresh=0.5): 4 y_pred = tf.cast(tf.greater(y_hat, thresh), tf.float32) 5 tp = tf.cast(tf.math.count_nonzero(y_pred * y, axis=0), tf.float32) 6 fp = tf.cast(tf.math.count_nonzero(y_pred * (1 - y), axis=0), tf.float32) 7 fn = tf.cast(tf.math.count_nonzero((1 - y_pred) * y, axis=0), tf.float32) 8 f1 = 2*tp / (2*tp + fn + fp + 1e-16) 9 macro_f1 = tf.reduce_mean(f1) 10 return macro_f1 11 12def main(): 13 14 (必要な変数は定義済) 15 16 # 学習 17 IMG_SHAPE = (img_size, img_size, channels) 18 base_model = tf.keras.applications.MobileNetV2(input_shape=IMG_SHAPE, 19 include_top=False, 20 weights='imagenet') 21 global_average_layer = tf.keras.layers.GlobalAveragePooling2D() 22 prediction_layer = tf.keras.layers.Dense(n_classes, activation='sigmoid') 23 model = tf.keras.Sequential([base_model,global_average_layer,prediction_layer]) 24 model.compile(optimizer=optimizers.SGD(lr=lr, momentum=momentum, nesterov=nesterov),loss='binary_crossentropy', metrics=[macro_f1]) 25 26 ckpt_cb = tf.keras.callbacks.ModelCheckpoint(checkpoint_path, 27 save_weights_only=True, 28 monitor='val_macro_f1', 29 mode='max', 30 verbose=1) 31 32 csv_logger = tf.keras.callbacks.CSVLogger(ckpt_dir+'/training.csv', separator=',') 33 34 #データ数の比は a:b:c:d = 14:1:14:1 35 class_weight = {0:0.07, 1:1, 2:0.0.07, 3:1} 36 37 history = model.fit(train_ds, 38 steps_per_epoch= int(num_train//batch_size), 39 validation_data=val_ds, 40 validation_steps= int(num_val//batch_size), 41 shuffle=True, 42 epochs=epochs, 43 class_weight = class_weight, 44 callbacks=[ckpt_cb, csv_logger],) 45 46 model.save_weights(ckpt_dir + '/my_checkpoint') 47

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

guest

回答2

0

python

1 2 #データ数の比は a:b:c:d = 1:14:1:14 3 class_weight = {0:0.07, 1:1, 2:0.0.07, 3:1}

逆にするべきでは? データ数が少ないクラスにより大きな重みを設定する必要があるはず。

投稿2021/05/20 15:12

編集2021/05/20 15:13
hayataka2049

総合スコア30939

orionza

2021/05/21 00:22

申し訳ありません、記載ミスでした。 検証した段階ではデータ数の少ないクラスに大きな重みを設定しておりました。
guest

0

少ない方の画像を水増しして学習すれば良いのではないでしょうか。

投稿2021/05/19 23:02

ppaul

総合スコア24672

orionza

2021/05/20 03:42

もちろん、画像の水増しやアンダーサンプリングでも学習自体は可能なのですが、今回は重みをつけて学習する方法について検討しております。お知恵をお貸しいただけますと大変助かります。
ppaul

2021/05/20 07:42

ご自分でディープラーニングを手作りされるなら、学習用データに学習率のデータを入れるように設計してシステムを組めばできないことはないと思います。しかし、ユーザニーズを考えると、tensorflowとかPyTorchにそういう機能は実装されていないでしょうし、将来も実装される可能性は低いと思います。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.29%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問