磐创AI分享
作者 | ashish0765
编译 | Flin
来源 | analyticsvidhya
什么是 Tensorflow 回调?
Tensorflow 回调是在训练深度学习模型时在特定时刻执行的函数或代码块。
我们都熟悉深度学习模型的训练过程。随着模型变得越来越复杂,训练时间也显着增加。因此,模型通常需要花费数小时来训练。
在训练模型之前的工作中,我们修复了所有选项和参数,例如学习率、优化器、损失等并开始模型训练。一旦训练过程开始,就无法暂停训练,以防我们想要更改一些参数。
此外,在某些情况下,当模型已经训练了几个小时,而我们想在后期调整一些参数时,这是不可能的。而这就是 TensorFlow 回调派上用场的地方。
如何使用回调
- 首先定义回调
- 在调用 model.fit() 时传递回调
# Stop training if NaN is encountered
NanStop = TerminateOnNaN()
# Decrease lr by 10%
LrValAccuracy = ReduceLROnPlateau(monitor='val_accuracy', patience=1, factor= 0.9, mode='max', verbose=0)
代码语言:javascript复制model.fit(X_train,y_train,
epochs=10,
validation_data=(X_test,y_test),
callbacks = [NanStop, LrValAccuracy])
让我们来看看一些最有用的回调
提前停止
当我们训练模型时,我们通常会查看指标以监控模型的表现。通常,如果我们看到极高的指标,我们可以得出结论,我们的模型过度拟合,如果我们的指标很低,那么我们就欠拟合了。
如果指标增加到某个范围以上,我们可以停止训练以防止过度拟合。EarlyStopping 回调允许我们做到这一点。
代码语言:javascript复制early_stop_cb = tf.keras.callbacks.EarlyStopping(
monitor='val_loss', min_delta=0, patience=0, verbose=0,
mode='auto'
)
- monitor:你在训练时要监视的指标
- min_delta:你要考虑作为对前一个时期的改进的指标的最小变化量
- patience:你等待指标等待的时期数。否则,你将停止训练。
- verbose:0:不打印任何内容,1:显示进度条,2:仅打印时期号
- mode :
- “auto” – 尝试从给定的指标中自动检测行为
- “min” – 如果指标停止下降,则停止训练
- “max” – 如果指标停止增加则停止训练
Lambda回调
此回调用于在训练过程中的特定时间调用某些 lambda 函数。
代码语言:javascript复制tf.keras.callbacks.LambdaCallback(
on_epoch_begin=None, on_epoch_end=None, on_batch_begin=None, on_batch_end=None,
on_train_begin=None, on_train_end=None, **kwargs
)
在这里,我们可以传递我们需要在指定时间执行的任何 lambda 函数。
让我们看看参数是什么意思
- on_epoch_begin:在每个时期开始时调用该函数。
- on_epoch_begin:在每个时期结束时调用该函数。
- on_batch_begin:在每批开始时调用该函数。
- on_batch_end:在每批结束时调用该函数。
- on_train_begin:模型开始训练时调用该函数
- on_train_end:模型训练完成时调用
print_batch_callback = LambdaCallback(
on_batch_begin=lambda bat,log: print(bat),
on_batch_begin=lambda bat,log: print(bat)
)
学习率调度器
训练过程中最常见的任务之一是改变学习率。通常,随着模型接近损失最小值(最佳拟合),我们逐渐开始降低学习率以获得更好的收敛性。
让我们看一个简单的例子,我们希望每 3 个 epoch 将学习率降低 5%。这里我们需要向 schedule 函数传递一个参数,该参数指定学习率变化的逻辑。
代码语言:javascript复制def schedule(epoch,lr):
if epoch % 3 == 0:
lr = lr - (lr*.05)
return lr
return lr
# Decrease lr by 5% for every 3rd epoch
LrScheduler = tf.keras.callbacks.LearningRateScheduler(schedule,verbose=1)
模型检查点
我们使用这个回调来以不同的频率保存我们的模型。这允许我们在中间步骤保存权重,以便在需要时我们可以稍后加载权重。
代码语言:javascript复制tf.keras.callbacks.ModelCheckpoint(
filepath, monitor='val_loss', verbose=0, save_best_only=False,
save_weights_only=False, mode='auto', save_freq='epoch'
)
filepath:模型所在的位置 monitor:要监视的度量 save_best_only:True:仅保存最好的模型,False:保存所有的模型时,指标改善 mode:min, max或auto save_weights_only:False:仅保存模型权重, True:同时保存模型权重和模型架构
例如,让我们看一个例子,保存具有最佳精度的模型
代码语言:javascript复制filePath = "models/Model1_weights.{epoch:02d}.hdf5"
model_checkpoint_callback = tf.keras.callbacksModelCheckpoint(
filepath=filePath,
save_weights_only=True,
monitor='val_accuracy',
mode='max')
这里我们使用一些模板字符串指定文件路径。{epoch:02d} 保存模型时由时期号代替
减少LROnPlateau
当特定指标停止增加并达到平台期时,此回调用于降低训练率。
代码语言:javascript复制tf.keras.callbacks.ReduceLROnPlateau(
monitor='val_loss', factor=0.1, patience=10, verbose=0,
mode='auto', min_delta=0.0001, cooldown=0, min_lr=0, **kwargs
)
factor:LR 减少的系数。新学习率 = old_learning_rate * 因子 min_delta:需要被视为改进的最小变化 cooldown:等待 LR 减少的时期数 min_lr:学习率不能低于该最小值
终止OnNaN
当任何损失变为 NaN 时,此回调将停止训练过程
代码语言:javascript复制tf.keras.callbacks.TerminateOnNaN()
Tensorboard
Tensorboard 允许我们显示有关训练过程的信息,如指标、训练图、激活函数直方图和其他梯度分布。
要使用Tensorboard,我们首先需要设置一个 log_dir,Tensorboard文件被保存到其中。
代码语言:javascript复制log_dir="logs"
tensorboard_callback = tf.keras.callbacks.TensorBoard(log_dir=log_dir, histogram_freq=1, write_graph=True)
- log_dir:保存文件的目录
- histogram_freq:计算直方图和梯度图的时期频率
- write_graph:我们是否需要在Tensorboard中显示和可视化图形
编写自己的回调
除了内置的回调之外,我们还可以为不同的目的定义和使用我们自己的回调。例如,假设我们要定义自己的度量标准,该度量标准在每个 epoch 结束时计算。
代码语言:javascript复制# Monitor MicroF1 and AUC Score
class Metrics_Callback(tf.keras.callbacks.Callback):
def __init__(self,x_val,y_val):
self.x_val = x_val
self.y_val = y_val
def on_train_begin(self, logs={}):
self.history = {"auc_score":[],"micro_f1":[]}
def on_epoch_end(self, epoch, logs={}):
auc_score = roc_auc_score(self.y_val, model.predict_proba(self.x_val))
y_true = [0 if x[0]==1.0 else 1 for x in self.y_val]
f1_s = f1_score(y_true,self.model.predict_classes(self.x_val), average='micro')
self.history["auc_score"].append(auc_score)
self.history["micro_f1"].append(f1_s)
代码语言:javascript复制Metrics = Metrics_Callback(X_test,y_test)
这里我们要计算每个 epoch 结束时的 F1 分数和 AUC 分数。在 init 方法中,我们读取计算分数所需的数据。然后在每个 epoch 结束时,我们在 on_epoch_end 函数中计算指标。
我们可以使用以下方法在不同的时间执行代码——
on_epoch_begin:在每个时期开始时调用。
on_epoch_begin:在每个时期结束时调用。
on_batch_begin:在每批开始时调用。
on_batch_end:在每批结束时调用。
on_train_begin:模型开始训练时调用
on_train_end:模型训练完成时调用
结论
这些是一些常用和最流行的回调。TensorFlow 官方文档为我们提供了有关各种其他回调及其相关用例的详细信息。
TensorFlow 官方文档:https://www.tensorflow.org/api_docs/python/tf/keras/callbacks/Callback