【问题标题】:tf.estimator.Estimator gives different test accuracy when trianed epoch by epoch vs over all epochstf.estimator.Estimator 给出不同的测试精度
【发布时间】:2019-10-02 13:50:16
【问题描述】:

我已经为 tf.estimator.Estimator 定义了一个简单的 CNN 作为我的 model_fn,并用这个 input_fn 提供给它:

def input_fn(features, labels, batch_size, epochs):
    dataset = tf.data.Dataset.from_tensor_slices((features))
    dataset = dataset.map(lambda x: tf.cond(tf.random_uniform([], 0, 1) > 0.5, lambda: dataset_augment(x), lambda: x),
                          num_parallel_calls=16).cache()
    dataset_labels = tf.data.Dataset.from_tensor_slices((labels))
    dataset = dataset.zip((dataset, dataset_labels))
    dataset = dataset.shuffle(30000)
    dataset = dataset.repeat(epochs)
    dataset = dataset.batch(batch_size)
    dataset = dataset.prefetch(-1)
    return dataset

当我以这种方式训练估计器时,我在 10 个 epoch 后获得了 43% 的测试准确率:

steps_per_epoch = data_train.shape[0] // batch_size
for epoch in range(1, epochs + 1):
    cifar100_classifier.train(lambda: input_fn(data_train, labels_train, batch_size, epochs=1), steps=steps_per_epoch)

但是当我以这种方式训练它时,我在 10 个 epoch 后获得了 32% 的测试准确率:

steps_per_epoch = data_train.shape[0] // batch_size
max_steps = epochs * steps_per_epoch
cifar100_classifier.train(steps=max_steps,
                              input_fn=lambda: input_fn(data_train, labels_train, batch_size, epochs=epochs))

我只是不明白为什么这两种方法会产生不同的结果。谁能解释一下?

【问题讨论】:

  • 如何设置cifar100_classifier?我的猜测是它与在第一种情况下重置的超参数有关。
  • @McAngus 我正在使用 tf.keras.layers 创建我的模型并使用 AdamOptimizer 对其进行训练。我假设检查点保持优化器的状态以及层的权重和偏差。因此,一次性训练模型与在每个 epoch 结束时从保存的检查点加载并继续训练另一个 epoch 等具有相同的效果......

标签: python tensorflow tensorflow-datasets tensorflow-estimator


【解决方案1】:

由于您在第一个示例中多次调用input_fn,因此您似乎将通过dataset_augment(x) 生成更多增强数据,因为您正在为每个x 每个时期进行增强硬币投掷。

在第二个示例中,您只需掷硬币一次,然后在同一数据上训练多个 epoch。所以这里你的训练集实际上是“更小”。

在第一个示例中,.cache() 并没有真正让您摆脱这种情况。

【讨论】:

  • 您实际上可以尝试从 input_fn 中删除 .cache() 并查看是否不会导致在两个公式中每个时期都调用增强,我不是 100% 了解地图如何与完全重复。
【解决方案2】:

你的模型的权重是随机初始化的吗?这可能是一种情况。

【讨论】:

  • 我正在使用 tf.keras.layers 并没有手动设置任何东西。但这对我的训练有何影响?不是从保存的检查点加载 tf.estimator.Estimator 对象(计算到该点的权重和变量),如果循环遍历该点,则从该点继续?
  • 当 nn 第一次初始化权重时,它使用了一些初始化方法,这就是为什么在不同的执行中不能有相同的输出。Conv2d 的默认 kernel_initializer 例如是“glorot_uniform”,您可以在此处的源代码中看到 github.com/keras-team/keras/blob/… 。以下是有关此初始化程序的一些信息:tensorflow.org/api_docs/python/tf/glorot_uniform_initializer。您可以尝试添加另一个初始化程序并设置种子值。
  • 我认为你误解了这个问题 :) 问题是在不同的运行中没有不同的结果。
猜你喜欢
  • 2020-05-23
  • 2018-04-17
  • 2021-07-12
  • 1970-01-01
  • 2021-06-15
  • 1970-01-01
  • 2021-09-14
  • 2022-11-28
  • 2016-03-21
相关资源
最近更新 更多