これはばかげた質問だと確信していますが、他の場所では見つけられないので、ここで質問します。
7つのラベルを持つケラスでcnn(unet)を使用してセマンティックイメージセグメンテーションを行っています。したがって、各画像の私のラベルは、theanoバックエンドを使用した(7、n_rows、n_cols)です。したがって、各ピクセルの7つのレイヤー全体で、ワンホットエンコードされます。この場合、カテゴリカルクロスエントロピーを使用するための正しい誤差関数はありますか?それは私にはそのように思えますが、ネットワークはバイナリのクロスエントロピー損失でよりよく学習するようです。なぜそうなるのか、そして原則的な目的は何かについて誰かが光を当てることはできますか?
バイナリクロスエントロピー損失は、最後のレイヤーのsigmod
アクティベーションで使用する必要があり、反対の予測に深刻なペナルティを課します。出力がワンホットコードであり、予測の合計が1であることは考慮されていません。ただし、予測の誤りがモデルに深刻なペナルティを課しているため、モデルは適切に分類することをやや学習しています。
ここで、ワンホットコードの事前適用を強制するには、カテゴリカルクロスエントロピーでsoftmax
アクティベーションを使用します。これを使用する必要があります。
現在、問題はsoftmax
を使用しています。Kerasは各ピクセルでsoftmaxをサポートしていないためです。
それを実行する最も簡単な方法は、Permute
レイヤーを使用して(n_rows、n_cols、7)に次元を並べ替え、次にReshape
レイヤーを使用して(n_rows * n_cols、7)に再形成することです。次に、softmax
アクティベーションレイヤーを追加して、クロスエントロピー損失を使用できます。データもそれに応じて再形成する必要があります。
そうするもう1つの方法は、depth-softmaxを実装することです。
def depth_softmax(matrix):
sigmoid = lambda x: 1 / (1 + K.exp(-x))
sigmoided_matrix = sigmoid(matrix)
softmax_matrix = sigmoided_matrix / K.sum(sigmoided_matrix, axis=0)
return softmax_matrix
ラムダレイヤーとして使用します。
model.add(Deconvolution2D(7, 1, 1, border_mode='same', output_shape=(7,n_rows,n_cols)))
model.add(Permute(2,3,1))
model.add(BatchNormalization())
model.add(Lambda(depth_softmax))
tf
image_dim_ordering
が使用されている場合は、Permute
レイヤーを使用できます。
詳細については、 ここ を確認してください。
私は@indraforyouの解決策をテストし、提案された方法にはいくつかの間違いがあると思います。コメントセクションでは適切なコードセグメントが許可されていないので、これが私が修正バージョンだと思うものです:
def depth_softmax(matrix):
from keras import backend as K
exp_matrix = K.exp(matrix)
softmax_matrix = exp_matrix / K.expand_dims(K.sum(exp_matrix, axis=-1), axis=-1)
return softmax_matrix
このメソッドは、マトリックスの順序が(高さ、幅、チャネル)であることを期待します。