问题描述
我正在尝试准备用于部署的自定义 Keras 模型,以便与 Tensorflow Serving 一起使用,但在预处理我的图像时遇到了问题.
I'm trying to prepare my custom Keras model for deploy to be used with Tensorflow Serving, but I'm running into issues with preprocessing my images.
当我训练我的模型时,我使用以下函数来预处理我的图像:
When i train my model i use the following functions to preprocess my images:
def process_image_from_tf_example(self, image_str_tensor, n_channels=3):
image = tf.image.decode_image(image_str_tensor)
image.set_shape([256, 256, n_channels])
image = tf.cast(image, tf.float32) / 255.0
return image
def read_and_decode(self, serialized):
parsed_example = tf.parse_single_example(serialized=serialized, features=self.features)
input_image = self.process_image_from_tf_example(parsed_example["image_raw"], 3)
ground_truth_image = self.process_image_from_tf_example(parsed_example["gt_image_raw"], 1)
return input_image, ground_truth_image
我的图像是保存在本地的 PNG,当我将它们写入我使用的 .tfrecord
文件时tf.gfile.GFile(str(image_path), 'rb').read()
My images are PNGs saved locally, and when i write them on the .tfrecord
files i usetf.gfile.GFile(str(image_path), 'rb').read()
这行得通,我可以训练我的模型并将其用于本地预测.
This works, I'm able to train my model and use it for local predictions.
现在我想部署我的模型以与 Tensorflow Serving 一起使用.我的 serving_input_receiver_fn
函数如下所示:
Now I want to deploy my model to be used with Tensorflow Serving. My serving_input_receiver_fn
function looks like this:
def serving_input_receiver_fn(self):
input_ph = tf.placeholder(dtype=tf.string, shape=[None], name='image_bytes')
images_tensor = tf.map_fn(self.process_image_from_tf_example, input_ph, back_prop=False, dtype=tf.float32)
return tf.estimator.export.ServingInputReceiver({'input_1': images_tensor}, {'image_bytes': input_ph})
其中 process_image_from_tf_example
与上述功能相同,但出现以下错误:
where process_image_from_tf_example
is the same function as above, but i get the following error:
InvalidArgumentError(回溯见上文):断言失败:[无法将字节解码为 JPEG、PNG、GIF 或 BMP]
阅读这里看起来这个错误是由于我不是使用tf.gfile.GFile(str(image_path), 'rb').read()
Reading here it looks like this error is due to the fact that i'm not usingtf.gfile.GFile(str(image_path), 'rb').read()
与我的训练/测试文件一样,但我无法使用它,因为我需要发送格式化为
as with my training/test files, but i can't use it because i need to send encoded bytes formatted as
{"image_bytes": {'b64': base64.b64encode(image).decode()}}
应 TF Serving 的要求.
as requested by TF Serving.
在线示例发送JPEG 编码字节并预处理以
Examples online send JPEG encoded bytes and preprocess the image starting with
tf.image.decode_jpeg(image_buffer, channels=3)
但是如果我在以
tf.image.decode_png(image_buffer, channels=3)
我收到以下错误:
InvalidArgumentError(回溯见上文):预期图像(JPEG、PNG 或 GIF),格式未知,以AAAAAAAAAAAAAAAA"开头
(顺便说一下,decode_jpeg
也是如此)
(the same happens with decode_jpeg
, by the way)
我做错了什么?你需要我提供更多代码来回答吗?非常感谢!
What am i doing wrong? Do you need more code from me to answer? Thanks a lot!
编辑!!改了标题,因为不够清楚
Edit!!Changed the title because it was not clear enough
推荐答案
好的,我解决了.
image
是一个 numpy 数组,但我必须执行以下操作:
image
was a numpy array but i had to do the following:
buffer = cv2.imencode('.jpg', image)[1].tostring()
bytes_image = base64.b64encode(buffer).decode('ascii')
{"image_bytes": {"b64": bytes_image}}
此外,我的预处理和 serving_input_receiver_fn
函数发生了变化:
Also, my preprocessing and serving_input_receiver_fn
functions changed:
def process_image_from_buffer(self, image_buffer):
image = tf.image.decode_jpeg(image_buffer, channels=3)
image = tf.image.convert_image_dtype(image, dtype=tf.float32)
image = tf.expand_dims(image, 0)
image = tf.image.resize_bilinear(image, [256, 256], align_corners=False)
image = tf.squeeze(image, [0])
image = tf.cast(image, tf.float32) / 255.0
return image
def serving_input_receiver_fn(self):
input_ph = tf.placeholder(dtype=tf.string, shape=[None])
images_tensor = tf.map_fn(self.process_image_from_buffer, input_ph, back_prop=False, dtype=tf.float32)
return tf.estimator.export.ServingInputReceiver({'input_1': images_tensor}, {'image_bytes': input_ph})
process_image_from_buffer
与上面用于训练的 process_image_from_tf_example
不同.我还从上面的 input_ph
中删除了 name='image_bytes'
.
process_image_from_buffer
is different than process_image_from_tf_example
used above for training.I also removed name='image_bytes'
from input_ph
above.
希望它足够清楚以帮助其他人.
Hope it's clear enough to help someone else.
这篇关于Tensorflow 服务:InvalidArgumentError:预期图像(JPEG、PNG 或 GIF),格式未知,以“AAAAAAAAAAAAAAAA"开头的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!