全局步骤不随批量规范和自定义估算器递增
Global step not incrementing with batch norm and custom estimator
我有一个客户估算器,它有几个层,在模型函数中如下所示:
natural_layer = tf.layers.dense(inputs = natural_layer,
units = units,
activation = None,
use_bias = False,
kernel_regularizer = params['regularizer'],
name = 'pre_batch_norm_layer_' + str(i + 1))
natural_layer = tf.layers.batch_normalization(natural_layer,
axis = 1,
center = True,
scale = True,
training = (mode == tf.estimator.ModeKeys.TRAIN),
name = 'batch_norm_layer_' + str(i + 1))
natural_layer = params['natural_layer_activation'](natural_layer, name = 'activation_layer_' + str(i + 1))
因为我使用的是 batch norm,训练操作是这样设置的:
update_ops = tf.get_collection(tf.GraphKeys.UPDATE_OPS)
with tf.control_dependencies(update_ops):
optimizer = tf.contrib.opt.MultitaskOptimizerWrapper(params['optimization_algorithm'](params['training_rate']))
train_op = optimizer.minimize(loss, global_step = tf.train.get_global_step())
优化器通常是tf.train.AdamOptimizer。
然而,当我去训练估计器时,全局步长永远不会增加(所以训练将永远 运行),我得到这个:
警告:tensorflow:似乎全局步骤(tf.train.get_global_step)没有增加。当前值(可能稳定):0 与先前值:0。您可以通过将 tf.train.get_global_step() 传递给 Optimizer.apply_gradients 或 Optimizer.minimize.
来增加全局步骤
我正在传递 tf.train.get_global_step() 以最小化,所以我不确定为什么它永远不会更新。我的直觉是它与批标准化有关,因为当我删除它或用 dropout 替换它时,一切正常(即使根据文档保留批标准化所需的更新操作行)。
有人知道这是怎么回事吗?如果有帮助,很高兴 post 更多代码。
我无法弄清楚为什么全局步骤没有自动递增,但是通过将其添加到 train_op 和 tf.group 来手动递增全局步骤是一个很好的解决方法。
update_ops = tf.get_collection(tf.GraphKeys.UPDATE_OPS)
with tf.control_dependencies(update_ops):
optimizer = tf.contrib.opt.MultitaskOptimizerWrapper(params['optimization_algorithm'](params['training_rate']))
train_op = optimizer.minimize(loss)
global_step = tf.train.get_global_step()
update_global_step = tf.assign(global_step, global_step + 1, name = 'update_global_step')
return tf.estimator.EstimatorSpec(mode, loss = loss, train_op = tf.group(train_op, update_global_step))
即使没有批量归一化,我也会遇到同样的问题。根据我的记忆,我能够通过在 sess.run
中调用 update_ops
以及 train_ops
来绕过它,而不是在 tf.control_dependencies
子句中。这可能只是 tensorflow 的一个错误。
我有一个客户估算器,它有几个层,在模型函数中如下所示:
natural_layer = tf.layers.dense(inputs = natural_layer,
units = units,
activation = None,
use_bias = False,
kernel_regularizer = params['regularizer'],
name = 'pre_batch_norm_layer_' + str(i + 1))
natural_layer = tf.layers.batch_normalization(natural_layer,
axis = 1,
center = True,
scale = True,
training = (mode == tf.estimator.ModeKeys.TRAIN),
name = 'batch_norm_layer_' + str(i + 1))
natural_layer = params['natural_layer_activation'](natural_layer, name = 'activation_layer_' + str(i + 1))
因为我使用的是 batch norm,训练操作是这样设置的:
update_ops = tf.get_collection(tf.GraphKeys.UPDATE_OPS)
with tf.control_dependencies(update_ops):
optimizer = tf.contrib.opt.MultitaskOptimizerWrapper(params['optimization_algorithm'](params['training_rate']))
train_op = optimizer.minimize(loss, global_step = tf.train.get_global_step())
优化器通常是tf.train.AdamOptimizer。
然而,当我去训练估计器时,全局步长永远不会增加(所以训练将永远 运行),我得到这个:
警告:tensorflow:似乎全局步骤(tf.train.get_global_step)没有增加。当前值(可能稳定):0 与先前值:0。您可以通过将 tf.train.get_global_step() 传递给 Optimizer.apply_gradients 或 Optimizer.minimize.
来增加全局步骤我正在传递 tf.train.get_global_step() 以最小化,所以我不确定为什么它永远不会更新。我的直觉是它与批标准化有关,因为当我删除它或用 dropout 替换它时,一切正常(即使根据文档保留批标准化所需的更新操作行)。
有人知道这是怎么回事吗?如果有帮助,很高兴 post 更多代码。
我无法弄清楚为什么全局步骤没有自动递增,但是通过将其添加到 train_op 和 tf.group 来手动递增全局步骤是一个很好的解决方法。
update_ops = tf.get_collection(tf.GraphKeys.UPDATE_OPS)
with tf.control_dependencies(update_ops):
optimizer = tf.contrib.opt.MultitaskOptimizerWrapper(params['optimization_algorithm'](params['training_rate']))
train_op = optimizer.minimize(loss)
global_step = tf.train.get_global_step()
update_global_step = tf.assign(global_step, global_step + 1, name = 'update_global_step')
return tf.estimator.EstimatorSpec(mode, loss = loss, train_op = tf.group(train_op, update_global_step))
即使没有批量归一化,我也会遇到同样的问题。根据我的记忆,我能够通过在 sess.run
中调用 update_ops
以及 train_ops
来绕过它,而不是在 tf.control_dependencies
子句中。这可能只是 tensorflow 的一个错误。