В Tensorflow, как использовать восстановленный мета-граф, если мета-граф питался входом TFRecord (без заполнителей)

Я обучил сеть с входным конвейером TFRecord. Другими словами, не было заполнителей. Простой пример будет:

input, truth = _get_next_batch()  # TFRecord. `input` is not a tf.placeholder
net = Model(input)
net.set_loss(truth)
optimizer = tf...(net.loss)

Допустим, я приобрел три файла, ckpt-20000.meta, ckpt-20000.data-0000-of-0001, ckpt-20000.index, Я понял, что позже можно импортировать мета-граф, используя .meta тензоры файлов и доступа, такие как:

new_saver = tf.train.import_meta_graph('ckpt-20000.meta')
new_saver.restore(sess, 'ckpt-20000')
logits = tf.get_collection("logits")[0]

Однако мета-граф не имеет заполнителя с самого начала в конвейере. Есть ли способ, которым я могу использовать мета-граф и вывод запроса ввода?

Для информации, в приложении запроса (или скрипте) я использовал определение модели с заполнителем и восстановленными весами модели (см. Ниже). Мне интересно, могу ли я просто использовать мета-граф без переопределения, так как это было бы намного проще.

input = tf.placeholder(...)
net = Model(input)
tf.restore(sess, 'ckpt-2000')
lgt = sess.run(net.logits, feed_dict = {input:img})

3 ответа

Решение

Вы можете построить график, который использует placeholder_with_default() для входов, поэтому можно использовать как TFRecord input pipeline так же как feed_dict{},

Пример:

input, truth = _get_next_batch()
_x = tf.placeholder_with_default(input, shape=[...], name='input')
_y = tf.placeholder_with_default(truth, shape-[...], name='label')

net = Model(_x)
net.set_loss(_y)
optimizer = tf...(net.loss)

Затем во время вывода

loaded_graph = tf.Graph()
with tf.Session(graph=loaded_graph) as sess:
  new_saver = tf.train.import_meta_graph('ckpt-20000.meta')
  new_saver.restore(sess, 'ckpt-20000')

  # Get the tensors by their variable name
  input = loaded_graph.get_tensor_by_name('input:0')
  logits = loaded_graph.get_tensor_by_name(...)

  # Now you can feed the inputs to your tensors
  lgt = sess.run(logits, feed_dict = {input:img})

В приведенном выше примере, если вы не вводите ввод, то вход будет считан из TFRecord input pipeline,

Есть ли способ сделать это без заполнителей при тестировании? Должна быть возможность повторно использовать график с новым входным конвейером, не прибегая к медленным заполнителям (т. Е. Набор тестовых данных может быть очень большим). placeholder_with_default является неоптимальным решением в этом случае.

Рекомендуемый способ - сохранить два мета-графика. Один для обучения / проверки / тестирования, а другой для вывода.

см. Построение SavedModel

export_dir = ...
...
builder = tf.saved_model_builder.SavedModelBuilder(export_dir)
with tf.Session(graph=tf.Graph()) as sess:
  ...
  builder.add_meta_graph_and_variables(sess,
                                       [tag_constants.TRAINING],
                                       signature_def_map=foo_signatures,
                                       assets_collection=foo_assets)
...
# Add a second MetaGraphDef for inference.
with tf.Session(graph=tf.Graph()) as sess:
  ...
  builder.add_meta_graph([tag_constants.SERVING])
...
builder.save()

Учебное пособие по NMT также предоставляет подробный пример создания нескольких графов с общими переменными: Neural Machine Translation (seq2seq) Учебное пособие по построению учебника, Eval и Выводные графы

train_graph = tf.Graph()
eval_graph = tf.Graph()
infer_graph = tf.Graph()

with train_graph.as_default():
  train_iterator = ...
  train_model = BuildTrainModel(train_iterator)
  initializer = tf.global_variables_initializer()

with eval_graph.as_default():
  eval_iterator = ...
  eval_model = BuildEvalModel(eval_iterator)

with infer_graph.as_default():
  infer_iterator, infer_inputs = ...
  infer_model = BuildInferenceModel(infer_iterator)

checkpoints_path = "/tmp/model/checkpoints"

train_sess = tf.Session(graph=train_graph)
eval_sess = tf.Session(graph=eval_graph)
infer_sess = tf.Session(graph=infer_graph)

train_sess.run(initializer)
train_sess.run(train_iterator.initializer)

for i in itertools.count():

  train_model.train(train_sess)

  if i % EVAL_STEPS == 0:
    checkpoint_path = train_model.saver.save(train_sess, checkpoints_path, global_step=i)
    eval_model.saver.restore(eval_sess, checkpoint_path)
    eval_sess.run(eval_iterator.initializer)
    while data_to_eval:
      eval_model.eval(eval_sess)

  if i % INFER_STEPS == 0:
    checkpoint_path = train_model.saver.save(train_sess, checkpoints_path, global_step=i)
    infer_model.saver.restore(infer_sess, checkpoint_path)
    infer_sess.run(infer_iterator.initializer, feed_dict={infer_inputs: infer_input_data})
    while data_to_infer:
      infer_model.infer(infer_sess)
Другие вопросы по тегам