Keras 中的自定义损失函数:初始化值并将值附加到循环中的张量
Custom loss function in Keras: Initializing and appending values to a Tensor in loop
我正在使用 Keras 和 Tensorflow 后端函数在 Keras 中编写自定义损失函数。我想最小化 f(y_true) 和 f(y_pred) 之间的均方误差,其中 f(y) 是非线性函数。
f(y) = [f1(y) f2(y) ... f12(y)], fk(y) = Xi_k*Theta_k(y), k = 1,2,...,12。 Xi_k 和 Theta_k(y) 是 1 阶张量。
由于 y_true 和 y_pred 的大小为 (batchSize x 15),我需要在循环中为训练批次中的所有样本计算 f(y) 的值 (I相信避免循环是不可能的)。循环操作的输出将是大小为 (batchSize x 12)
的张量
[[f(y_true[1,:])],[f(y_true[2,:])],...,[f(y_true[batchSize,:])]]
和
[[f(y_pred[1,:])],[f(y_pred[2,:])],...,[f(y_pred[batchSize,:])]]
通常,在处理数组或矩阵时,我们会初始化一个所需大小的矩阵并在循环中为其赋值,或者我们创建一个空矩阵并在循环中为其附加值。但是我们如何对张量做同样的事情呢?
下面是自定义损失函数的简化形式(只计算f1(y_true)和f1(y_pred))。初始化和附加函数不起作用,因为它们不是 tf/Keras 操作,我应该用什么来代替它们以使其与张量一起工作?
matd = spio.loadmat('LPVmodel_iVarDeg.mat', squeeze_me=True)
mate = spio.loadmat('PNLSS_model_modified.mat', squeeze_me=True)
def custom_loss_fn(y_true, y_pred):
iVarDeg1 = tf.convert_to_tensor(matd['iVarDeg1'], dtype=tf.float32) # (XiSize(1) x 15)
Xi1 = tf.convert_to_tensor(mate['Xim1'], dtype=tf.float32) # (XiSize(1) x 1)
batchSize = m
fy_true = [] # initialization
fy_pred = [] # initialization
for i in range(batchSize):
yin = y_true[i,:] # (1 x 15) network output
tin = y_pred[i,:] # (1 x 15) target
ypowerD = tf.math.pow(yin,iVarDeg1) # element wise power (XiSize(1)x15)
monomial = tf.math.reduce_prod(ypowerD) # column wise product of elements (XiSize(1)x1)
Theta1 = monomial # nonlinear basis for state eq 1 (XiSize(1)x1)
ypowerD = tf.math.pow(tin,iVarDeg1)
monomial = tf.math.reduce_prod(ypowerD)
Gamma1 = monomial
temp = tf.math.reduce_sum(tf.math.multiply(Xi1,Theta1)) # sum(element wise prod)
fy_true.append(temp)
temp = tf.math.reduce_sum(tf.math.multiply(Xi1,Gamma1))
fy_pred.append(temp)
return Kb.mean(Kb.sum(Kb.square(fy_pred - fy_true))
在图形模式下,如果你想像列表一样在循环中填充张量,你可以使用 TensorArray :
到'initialise'例如:
ta = tf.TensorArray(tf.float32, size=0, dynamic_size=True, clear_after_read=False)
至'append':
ta = ta.write(1, 20)
将 TensorArray 转换为张量:
ta.stack()
我正在使用 Keras 和 Tensorflow 后端函数在 Keras 中编写自定义损失函数。我想最小化 f(y_true) 和 f(y_pred) 之间的均方误差,其中 f(y) 是非线性函数。
f(y) = [f1(y) f2(y) ... f12(y)], fk(y) = Xi_k*Theta_k(y), k = 1,2,...,12。 Xi_k 和 Theta_k(y) 是 1 阶张量。
由于 y_true 和 y_pred 的大小为 (batchSize x 15),我需要在循环中为训练批次中的所有样本计算 f(y) 的值 (I相信避免循环是不可能的)。循环操作的输出将是大小为 (batchSize x 12)
的张量[[f(y_true[1,:])],[f(y_true[2,:])],...,[f(y_true[batchSize,:])]]
和
[[f(y_pred[1,:])],[f(y_pred[2,:])],...,[f(y_pred[batchSize,:])]]
通常,在处理数组或矩阵时,我们会初始化一个所需大小的矩阵并在循环中为其赋值,或者我们创建一个空矩阵并在循环中为其附加值。但是我们如何对张量做同样的事情呢?
下面是自定义损失函数的简化形式(只计算f1(y_true)和f1(y_pred))。初始化和附加函数不起作用,因为它们不是 tf/Keras 操作,我应该用什么来代替它们以使其与张量一起工作?
matd = spio.loadmat('LPVmodel_iVarDeg.mat', squeeze_me=True)
mate = spio.loadmat('PNLSS_model_modified.mat', squeeze_me=True)
def custom_loss_fn(y_true, y_pred):
iVarDeg1 = tf.convert_to_tensor(matd['iVarDeg1'], dtype=tf.float32) # (XiSize(1) x 15)
Xi1 = tf.convert_to_tensor(mate['Xim1'], dtype=tf.float32) # (XiSize(1) x 1)
batchSize = m
fy_true = [] # initialization
fy_pred = [] # initialization
for i in range(batchSize):
yin = y_true[i,:] # (1 x 15) network output
tin = y_pred[i,:] # (1 x 15) target
ypowerD = tf.math.pow(yin,iVarDeg1) # element wise power (XiSize(1)x15)
monomial = tf.math.reduce_prod(ypowerD) # column wise product of elements (XiSize(1)x1)
Theta1 = monomial # nonlinear basis for state eq 1 (XiSize(1)x1)
ypowerD = tf.math.pow(tin,iVarDeg1)
monomial = tf.math.reduce_prod(ypowerD)
Gamma1 = monomial
temp = tf.math.reduce_sum(tf.math.multiply(Xi1,Theta1)) # sum(element wise prod)
fy_true.append(temp)
temp = tf.math.reduce_sum(tf.math.multiply(Xi1,Gamma1))
fy_pred.append(temp)
return Kb.mean(Kb.sum(Kb.square(fy_pred - fy_true))
在图形模式下,如果你想像列表一样在循环中填充张量,你可以使用 TensorArray :
到'initialise'例如:
ta = tf.TensorArray(tf.float32, size=0, dynamic_size=True, clear_after_read=False)
至'append':
ta = ta.write(1, 20)
将 TensorArray 转换为张量:
ta.stack()