我刚刚开始学习Tensorflow和Keras,我想知道是否还有另一种方法(更手动地)在不使用拟合方法的情况下训练模型。
我想手动执行优化过程:我想使用自己的损失函数自己更新参数,并用我计算出的损失更新这些参数。
有没有办法做到这一点,或者我吓坏了?
我之所以这样问,是因为我想了解更多Keras模型的工作原理,以及是否有任何方法可以在不使用fit方法的情况下训练网络,这看起来像在做很多事情。
请看一下本教程:Tensorflow - Custom training。解释了如何创建自己的损失函数,自定义优化器以及如何定义训练循环。您可以完全控制培训过程。
我在这里复制了您可能最感兴趣的代码:
# Custom loss
def loss(target_y, predicted_y):
return tf.reduce_mean(tf.square(target_y - predicted_y))
# Define a training loop
def train(model, inputs, outputs, learning_rate):
with tf.GradientTape() as t:
current_loss = loss(outputs, model(inputs))
dW, db = t.gradient(current_loss, [model.W, model.b])
model.W.assign_sub(learning_rate * dW)
model.b.assign_sub(learning_rate * db)
model = Model()
Ws, bs = [], []
epochs = range(10)
for epoch in epochs:
Ws.append(model.W.numpy())
bs.append(model.b.numpy())
current_loss = loss(outputs, model(inputs))
train(model, inputs, outputs, learning_rate=0.1)
print('Epoch %2d: W=%1.2f b=%1.2f, loss=%2.5f' %
(epoch, Ws[-1], bs[-1], current_loss))
该教程使用了一个非常简单的线性模型,但是对于理解这一点非常有用。但是,如果您对更复杂的东西感兴趣,请查看本教程:Tensorflow - Custom training: walkthrough
#Create the model
model = tf.keras.Sequential([
tf.keras.layers.Dense(10, activation=tf.nn.relu, input_shape=(4,)), # input shape required
tf.keras.layers.Dense(10, activation=tf.nn.relu),
tf.keras.layers.Dense(3)
])
# You can define your own loss function here
loss_object = tf.keras.losses.SparseCategoricalCrossentropy(from_logits=True)
def loss(model, x, y, training):
# training=training is needed only if there are layers with different
# behavior during training versus inference (e.g. Dropout).
y_ = model(x, training=training)
return loss_object(y_true=y, y_pred=y_)
# Create here your gradient and optimizor
def grad(model, inputs, targets):
with tf.GradientTape() as tape:
loss_value = loss(model, inputs, targets, training=True)
return loss_value, tape.gradient(loss_value, model.trainable_variables)
optimizer = tf.keras.optimizers.SGD(learning_rate=0.01)
# Training loop
train_loss_results = []
train_accuracy_results = []
num_epochs = 201
for epoch in range(num_epochs):
epoch_loss_avg = tf.keras.metrics.Mean()
epoch_accuracy = tf.keras.metrics.SparseCategoricalAccuracy()
# Training loop - using batches of 32
for x, y in train_dataset:
# Optimize the model
loss_value, grads = grad(model, x, y)
optimizer.apply_gradients(zip(grads, model.trainable_variables))
# Track progress
epoch_loss_avg.update_state(loss_value) # Add current batch loss
# Compare predicted label to actual label
# training=True is needed only if there are layers with different
# behavior during training versus inference (e.g. Dropout).
epoch_accuracy.update_state(y, model(x, training=True))
# End epoch
train_loss_results.append(epoch_loss_avg.result())
train_accuracy_results.append(epoch_accuracy.result())
if epoch % 50 == 0:
print("Epoch {:03d}: Loss: {:.3f}, Accuracy: {:.3%}".format(epoch,
epoch_loss_avg.result(),
epoch_accuracy.result()))