ニューラルネットワークのマルチクラス、マルチラベル分類タスクの損失関数は何ですか?


64

ニューラルネットワークをトレーニングして、オブジェクトのセットをnクラスに分類しています。各オブジェクトは、同時に複数のクラスに属することができます(マルチクラス、マルチラベル)。

マルチクラス問題の場合、一般に、mseの代わりにソフトマックスとカテゴリクロスエントロピーを損失関数として使用することをお勧めしますが、その理由はだいたいわかります。

マルチラベルの私の問題については、各クラスの確率が互いに独立している必要があるため、もちろんソフトマックスを使用することは意味がありません。したがって、最後のレイヤーは、入力をすべてのクラスの確率範囲0..1に押しつぶすシグモイドユニットです。

今、私はこれにどの損失関数を使用すべきかわからない。カテゴリクロスエントロピーの定義を見ると、1になるはずのニューロンの出力のみが考慮され、他のニューロンは無視されるため、この問題にはあまり当てはまらないと思います。

バイナリクロスエントロピーは、より適切に聞こえますが、出力ニューロンが1つの場合のバイナリ分類の問題については、これまでに言及しただけです。

重要な場合に備えて、トレーニングにpythonとkerasを使用しています。


1
softmax 「入力を各クラスの確率範囲0..1に押しつぶすシグモイドユニット」であると思います。
大井紅

損失関数としてsoftmaxを使用し、確率を使用してデータにマルチラベルを付けることができます。
バルボア

回答:


30

ケラスを使用している場合は、出力層にシグモイドを、コスト関数にbinary_crossentropyを配置するだけです。

テンソルフローを使用している場合、sigmoid_cross_entropy_with_logitsを使用できます。しかし、私の場合、この直接損失関数は収束しませんでした。だから、明示的なシグモイドクロスエントロピー損失を使用することになりました。この例のように独自に作成できます(yln(sigmoid(logits))+(1y)ln(1sigmoid(logits)))

シグモイドは、softmaxとは異なり、出力として周りの確率分布を与えませんが、独立した確率を与えます。nclasses

行に割り当てられるラベルの平均が少ない場合、softmax_cross_entropy_with_logitsを使用できます。これは、クラスが相互に排他的である間にこの損失が発生するため、その確率は必ずしも必要ではないためです。必要なのは、ラベルの各行が有効な確率分布であることだけです。そうでない場合、勾配の計算は不正確になります。


Alok様、OPにこの関数の使用方法と、なぜ理にかなっているのかをOPに説明できますか?ツアーで見るように、サイトではリンクのみの回答は推奨されていません。
アントワーヌヴェルネ

良い短い説明はkeras githubで見ることができます:github.com/fchollet/keras/issues/741
Dror

1
クロスエントロピーを使用する場合、独自のコスト関数を記述することはお勧めしません- 数値の安定性の問題が発生する可能性があります。議論についてはgithub.com/tensorflow/tensorflow/issues/2462をご覧ください。
kbrose

1つはマルチラベル、もう1つはマルチラベルマルチクラスです。シグモイドは出力を0〜1に押しつぶしますが、OPには複数のクラスがあるため、出力はEg 0〜10になります。したがって、出力は[0,5,2,3,1] <---これはシグモイドではありませんします。
-mimoralea

コスト関数で使用する前にtf.round(logits)する必要がありますか、隠れ層からtf.nn.sigmoid ....に直接ロジットを使用できますか?
モンク

9

更新(18/04/18):古い答えは私のモデルでまだ有用であることが証明されました。トリックは、パーティション関数と分布を別々にモデル化し、softmaxのパワーを活用することです。

観測ベクトルがラベルを含むとします。 (サンプルiにラベルmが含まれる場合は1、それ以外の場合は0)。したがって、目的は、サンプルごとにマトリックスをモデル化することです。したがって、モデルはます。を展開して、2つの特性を実現することを検討してください。ymyim=δimF(yi,xi)=logP(yi|xi)yim=ZP(ym)

  1. 分布関数:mP(ym)=1
  2. パーティション関数:はラベルの数を推定しますZ

次に、2つを別々にモデリングする必要があります。分布関数は、ソフトマックスレイヤーで最適にモデル化され、パーティション関数は線形単位でモデル化できます(実際には、としてクリップしました。ポアソンユニットのようなより洗練されたモデリングがおそらくうまく機能します)。次に、分散損失(ディストリビューションでKL、パーティションでMSE)を適用するか、製品で次の損失を試すかを選択できます。max(0.01,output)

実際には、オプティマイザーの選択も大きな違いをもたらします。因数分解アプローチでの私の経験は、Adadeltaの下で最もうまく機能することです(Adagradは私には役に立たず、まだRMSpropを試していません。SGDのパフォーマンスはパラメーターの影響を受けます)。

シグモイドに関するサイドコメント:私は確かにシグモイド+クロスエントロピーを試しましたが、うまくいきませんでした。モデルはのみを予測する傾向があり、分布関数の変動を捕捉できませんでした。(別名、それはパーティションのモデリングに何らかの形で非常に有用であり、その背後に数学的な理由があります)Z

更新:(ランダムに考えた)Dirichletプロセスを使用すると、ラベルの数にいくつかの事前の組み込みが可能になると思われますか?

更新:実験により、修正されたKL発散は、マルチラベル出力ではなく、マルチクラス出力を与える傾向があります。


(旧回答)

シグモイドのクロスエントロピーに関する私の経験はあまり快適ではありませんでした。現時点では、修正KL発散を使用しています。それは形をとります

Loss(P,Q)=x|P(x)Q(x)||logP(x)Q(x)|=x|(P(x)Q(x))logP(x)Q(x)|
ここで、はターゲットの擬似分布であり、は予測される擬似分布です(ただし、関数は実際には対称なので、実際には問題になりません)P(x)Q(x)

それらは、正規化されていないため、疑似分布と呼ばれます。したがって、特定のサンプルに2つのラベルがある場合、ます。xP(x)=2

ケラスの推進力

def abs_KL_div(y_true, y_pred):
    y_true = K.clip(y_true, K.epsilon(), None)
    y_pred = K.clip(y_pred, K.epsilon(), None)
    return K.sum( K.abs( (y_true- y_pred) * (K.log(y_true / y_pred))), axis=-1)

私の特定のデータセットでadamは、よりもはるかに優れていましたrmsprop
-shadi

そのような損失をトレーニングに使用する場合、テスト段階でそれを行う方法は?また、予測にsoftmaxを使用しますが、マルチラベルクラスを決定するためのしきい値の選択方法は?
karl_TUM


0

実際にテンソルフローではsigmoid_cross_entropy_mean、マルチラベルの損失計算関数として使用することができます、私はそれを非常に確認しています


ドキュメントへのリンクをお知らせください
-Ivelin

0

私はここでは初心者ですが、この質問で試してみましょう。私はあなたと同じものを検索していましたが、最終的に非常に優れたkerasマルチクラス分類チュートリアル@ http://machinelearningmastery.com/multi-class-classification-tutorial-keras-deep-learning-library/を見つけました。

このチュートリアルの作成者は、カテゴリクロスエントロピー損失関数を使用しています。また、ここで解決策を見つけるのに役立つスレッドが他にもあります


3
それはマルチクラスだけでなく、マルチラベルでもあります。
モンク
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.