【问题标题】:How to use tf.data's initializable iterator and reinitializable interator and feed data to estimator api?如何使用 tf.data 可初始化迭代器和可初始化迭代器并将数据提供给 estimator api?
【发布时间】:2019-01-08 13:36:46
【问题描述】:

所有的官方谷歌教程都对所有的 estimator api 实现使用一次性迭代器,我找不到任何关于如何使用 tf.data 的可初始化迭代器和可重新初始化的迭代器而不是一次性迭代器的文档。

谁能告诉我如何使用 tf.data 的可初始化迭代器和可重新初始化的迭代器在 train_data 和 test_data 之间切换。我们需要运行一个会话来使用 feed dict 并在可初始化的迭代器中切换数据集,它是一个低级 api,并且如何使用它是 estimator api 架构的一部分

PS:我确实发现谷歌提到 “注意:目前,一次性迭代器是唯一可以轻松与 Estimator 一起使用的类型。”

但是社区内有什么解决办法吗?或者我们应该出于某种充分的理由坚持使用一次迭代器

【问题讨论】:

  • 只是好奇:在您开始使用Estimator 之前,您是否使用过from_string_handle
  • 不,我刚开始使用估算器,@EricAuld 我能知道你为什么问吗?

标签: python tensorflow tensorflow-datasets tensorflow-estimator


【解决方案1】:

要使用可初始化或可重新初始化的迭代器,您必须创建一个继承自 tf.train.SessionRunHook 的类。然后此类可以访问 tf.estimator 函数使用的会话。

这是一个快速示例,您可以根据自己的需要进行调整:

class IteratorInitializerHook(tf.train.SessionRunHook):
    def __init__(self):
        super(IteratorInitializerHook, self).__init__()
        self.iterator_initializer_func = None # Will be set in the input_fn

    def after_create_session(self, session, coord):
        self.iterator_initializer_func(session) 


def get_inputs(X, y):
    iterator_initializer_hook = IteratorInitializerHook()

    def input_fn():
        X_pl = tf.placeholder(X.dtype, X.shape)
        y_pl = tf.placeholder(y.dtype, y.shape)

        dataset = tf.data.Dataset.from_tensor_slices((X_pl, y_pl))
        dataset = ...
        ...

        iterator = dataset.make_initializable_iterator()
        next_example, next_label = iterator.get_next()


        iterator_initializer_hook.iterator_initializer_func = lambda sess: sess.run(iterator.initializer,
                                                                                    feed_dict={X_pl: X, y_pl: y})

        return next_example, next_label

    return input_fn, iterator_initializer_hook

...

train_input_fn, train_iterator_initializer_hook = get_inputs(X_train, y_train)
test_input_fn, test_iterator_initializer_hook = get_inputs(X_test, y_test)

...

estimator.train(input_fn=train_input_fn,
                hooks=[train_iterator_initializer_hook])
estimator.evaluate(input_fn=test_input_fn,
                   hooks=[test_iterator_initializer_hook])

这是我在blogpost by Sebastian Pölsterl 中找到的代码的修改版本。查看“通过数据集 API 向 Estimator 提供数据”部分。

【讨论】:

  • 我需要试验一下你的方法会让你及时更新,谢谢
  • 这个方法在k-d-w.org/blog/103/…也有说明
  • 谢谢!我完全忘记了我最初是从哪里得到这个的。将其添加到答案中。
【解决方案2】:

或者你可以简单地使用tf.estimator.train_and_evaluate https://www.tensorflow.org/api_docs/python/tf/estimator/train_and_evaluate 它允许您在训练期间使用验证,而根本不需要关心迭代器。

【讨论】:

  • tf.estimator.train_and_evaluate 只是一个包装器,根本不回答这个问题。如果您出于任何原因需要使用 feed_dict(在我的示例中为输入占位符赋值),您需要一个可初始化的迭代器和一个 tf.train.SessionRunHook
  • 如果你只需要在train和test之间切换,为什么不使用train_and_evaluate呢?
  • 如果您的输入函数可以使用one_shot_iterator 初始化,那么您可以使用tf.estimator.train_and_evaluate 或在estimator.trainestimator.evaluate 之间交替使用,但并非所有输入函数都是这种情况(例如,如果您的数据集 > 2 GB)并且问题清楚地表明他们需要传递一个提要字典。我还建议您远离one_shot_iterator,因为它会使您的输入图变得非常大。
猜你喜欢
  • 2017-12-14
  • 1970-01-01
  • 1970-01-01
  • 2010-11-18
  • 2012-02-09
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-02-07
相关资源
最近更新 更多