这边的other_loss 能计算出值,但是梯度回传都是0 , 要怎么修改,才能正确回传? 目的是,在原有分类损失上,增加OK(第1类)和NG(除1之外的类)损失。让模型分类对的同时,注重NG和OK之间分类。
class Combined_loss(losses.Loss): # 继承Loss类
def __init__(self, base_loss,weight=[0.5,0.5],ng_select="max", **kwargs):
#ng_select : ng的值选取方法,“max”取最大值做代表,“mean” 取ng的平均值做代表,"sum"代表累加
super(Combined_loss, self).__init__(**kwargs)
self.base_loss = base_loss
self.weight = weight
self.other_loss = tf.keras.losses.CategoricalCrossentropy(label_smoothing = 0.1)
self.ng_select = ng_select
def call(self, y_true, y_pred): #默认第一类是OK ,其余是NG
new_y_true = []
new_y_pred = []
if(self.ng_select =="max"):
ng_pred_argmax = tf.math.argmax(y_pred[:,1:],axis=1).numpy()
ng_true_argmax = tf.math.argmax(y_true[:,1:],axis=1)
for index in range(len(ng_pred_argmax)):
new_y_true.append([y_true[index, 0], y_true[index, ng_true_argmax[index] + 1]])
new_y_pred.append([y_pred[index, 0], y_pred[index, ng_pred_argmax[index] + 1]])
elif(self.ng_select =="mean"):
ng_pred_mean = tf.math.reduce_mean(y_pred[:, 1:], axis=1)
ng_true_argmax = tf.math.argmax(y_true[:, 1:], axis=1)
for index in range(len(ng_pred_mean)):
new_y_true.append([y_true[index, 0], y_true[index, ng_true_argmax[index] + 1]])
new_y_pred.append([y_pred[index, 0], ng_pred_mean[index]])
elif(self.ng_select =="sum"):
ng_pred_sum = tf.math.reduce_sum(y_pred[:, 1:], axis=1)
ng_true_sum = tf.math.reduce_sum(y_true[:, 1:], axis=1)
for index in range(len(ng_pred_sum)):
new_y_true.append([y_true[index, 0], ng_true_sum[index]])
new_y_pred.append([y_pred[index, 0], ng_pred_sum[index]])
new_y_true = np.array(new_y_true)
new_y_pred = np.array(new_y_pred)
new_y_pred = tf.convert_to_tensor(new_y_pred)
loss = self.base_loss(y_true,y_pred) * self.weight[0] + self.weight[1]* self.other_loss(new_y_true,new_y_pred)
return loss
other_loss 能得到值,但是屏蔽base_loss时,梯度全部是0 。 梯度没回传。
想要达到 other_loss的值能够回传调整模型。