1 回答

TA貢獻1891條經(jīng)驗 獲得超3個贊
我認為問題在于您在第一個版本中無意中進行了廣播操作,這給您帶來了錯誤的結果。如果您的批次(?, 1)由于tf.squeeze操作而具有 shape ,則會發(fā)生這種情況。注意本例中的形狀
import tensorflow as tf
# Make random y_true and y_pred with shape (10, 1)
tf.random.set_seed(10)
y_true = tf.dtypes.cast(tf.random.uniform((10, 1), 0, 3, dtype=tf.int32), tf.float32)
y_pred = tf.random.uniform((10, 1), 0, 1, dtype=tf.float32)
# first
y_t = tf.squeeze(y_true)
mask = tf.where(y_t != 2)
y_t = tf.gather_nd(y_t, mask)
tf.print(tf.shape(y_t))
# [7]
y_p = tf.gather_nd(y_pred, mask)
tf.print(tf.shape(y_p))
# [7 1]
loss = tf.keras.losses.binary_crossentropy(y_t, y_p)
first_loss = tf.reduce_mean(loss)
tf.print(tf.shape(loss), summarize=-1)
# [7]
tf.print(first_loss, summarize=-1)
# 0.884061277
# second
mask = tf.where(y_true!=2, True, False)
y_t = y_true[mask]
tf.print(tf.shape(y_t))
# [7]
y_p = y_pred[mask]
tf.print(tf.shape(y_p))
# [7]
loss = tf.keras.losses.binary_crossentropy(y_t, y_p)
tf.print(tf.shape(loss), summarize=-1)
# []
second_loss = tf.reduce_mean(loss)
tf.print(second_loss, summarize=-1)
# 1.15896356
在第一個版本中, 和y_t都y_p被廣播到 7x7 張量中,因此交叉熵基本上是“全部對全部”計算的,然后求平均值。在第二種情況下,僅計算每對對應值的交叉熵,這是正確的做法。
如果您只是刪除tf.squeeze上面示例中的操作,結果就會得到糾正。
添加回答
舉報