尝试将Keras模型导出为TensorFlow Estimator以便服务模型时遇到以下问题。由于该问题的答案中也弹出相同的问题,因此,我将说明玩具示例中发生的情况,并提供用于文档目的的解决方法。Tensorflow 1.12.0和Keras 2.2.4会发生此行为。实际的Keras和tf.keras。
tf.keras
尝试导出使用Keras模型从Keras模型创建的Estimator时出现问题tf.keras.estimator.model_to_estimator。调用时estimator.export_savedmodel,将抛出aNotFoundError或a ValueError。
tf.keras.estimator.model_to_estimator
estimator.export_savedmodel
NotFoundError
ValueError
下面的代码将其复制为一个玩具示例。
创建Keras模型并保存:
import keras model = keras.Sequential() model.add(keras.layers.Dense(units=1, activation='sigmoid', input_shape=(10, ))) model.compile(loss='binary_crossentropy', optimizer='sgd') model.save('./model.h5')
接下来,使用将模型转换为estimator tf.keras.estimator.model_to_estimator,添加输入接收器函数并使用以下Savedmodel格式将其导出estimator.export_savedmodel:
Savedmodel
# Convert keras model to TF estimator tf_files_path = './tf' estimator =\ tf.keras.estimator.model_to_estimator(keras_model=model, model_dir=tf_files_path) def serving_input_receiver_fn(): return tf.estimator.export.build_raw_serving_input_receiver_fn( {model.input_names[0]: tf.placeholder(tf.float32, shape=[None, 10])}) # Export the estimator export_path = './export' estimator.export_savedmodel( export_path, serving_input_receiver_fn=serving_input_receiver_fn())
这将抛出:
ValueError: Couldn't find trained model at ./tf.
我的解决方法如下。检查./tf文件夹可以清楚地看到,model_to_estimator将必要文件存储在keras子文件夹中的调用,同时export_model希望这些文件./tf直接位于文件夹中,因为这是我们为model_dir参数指定的路径:
./tf
model_to_estimator
keras
export_model
model_dir
$ tree ./tf ./tf └── keras ├── checkpoint ├── keras_model.ckpt.data-00000-of-00001 ├── keras_model.ckpt.index └── keras_model.ckpt.meta 1 directory, 4 files
一种简单的解决方法是将这些文件上移一个文件夹。这可以使用Python完成:
import os import shutil from pathlib import Path def up_one_dir(path): """Move all files in path up one folder, and delete the empty folder """ parent_dir = str(Path(path).parents[0]) for f in os.listdir(path): shutil.move(os.path.join(path, f), parent_dir) shutil.rmtree(path) up_one_dir('./tf/keras')
这将使model_dir目录如下所示:
$ tree ./tf ./tf ├── checkpoint ├── keras_model.ckpt.data-00000-of-00001 ├── keras_model.ckpt.index └── keras_model.ckpt.meta 0 directories, 4 files
在model_to_estimator和export_savedmodel调用之间进行此操作可以根据需要导出模型:
export_savedmodel
export_path = './export' estimator.export_savedmodel( export_path, serving_input_receiver_fn=serving_input_receiver_fn())
INFO:tensorflow:SavedModel写入:./export/temp-b‘1549796240’/saved_model.pb