tflite量化如何更改输入dtype

时间:2020-06-18 09:15:01

标签: python tensorflow keras quantization tf-lite

在文章末尾查看可能的解决方案


我正在尝试对rcmalli中的keras-vggface模型进行完全量化以在NPU上运行。该模型是Keras模型(不是tf.keras)。

使用TF 1.15进行以下量化时:

print(tf.version.VERSION)
num_calibration_steps=5

converter = tf.lite.TFLiteConverter.from_keras_model_file('path_to_model.h5')        

#converter.post_training_quantize = True  # This only makes the weight in8 but does not initialize model quantization  
def representative_dataset_gen():
    for _ in range(num_calibration_steps):
        pfad='path_to_image(s)'
        img=cv2.imread(pfad)
        # Get sample input data as a numpy array in a method of your choosing.
        yield [img]
converter.representative_dataset = representative_dataset_gen
tflite_quant_model = converter.convert()
open("quantized_model", "wb").write(tflite_quant_model)

模型已转换,但由于我需要完整的int8量化,因此我添加:

converter.target_spec.supported_ops = [tf.lite.OpsSet.TFLITE_BUILTINS_INT8]
converter.inference_input_type = tf.int8  # or tf.uint8
converter.inference_output_type = tf.int8  # or tf.uint8

出现此错误消息:

ValueError:无法设置张量:获得类型为UINT8的值,但预期输入0为FLOAT32类型,名称:input_1

显然,模型的输入仍然需要float32。

问题

  1. 我是否必须适应更改输入dtype的量化方法?或
  2. 是否必须事先将模型的输入层更改为dtype int8?
  3. 或者是实际上在报告该模型尚未真正量化?

如果答案是1或2,那么您还会为我提供最佳实践提示吗?


添加

使用:

h5_path = 'my_model.h5'
model = keras.models.load_model(h5_path)
model.save(os.getcwd() +'/modelTF2') 

使用TF 2.2将h5保存为pb,然后使用converter=tf.lite.TFLiteConverter.from_saved_model(saved_model_dir)

就像TF 2.x tflite接受浮点数,然后将它们转换为uint8s internally一样。我认为这可能是一个解决方案。不幸的是,出现此错误消息:

tf.lite.TFLiteConverter.from_keras_model赋予'str'对象没有属性'call'

显然,TF2.x无法处理纯Keras模型。

使用tf.compat.v1.lite.TFLiteConverter.from_keras_model_file()解决此错误只是重复上面的错误,因为我们又回到了“ TF 1.15”级别。


加法2

另一种解决方案是将keras模型手动转移到tf.keras。如果没有其他解决方案,我会进行调查。


关于Meghna Natraj的评论

要重新创建模型(使用TF 1.13.x),只需:

pip install git+https://github.com/rcmalli/keras-vggface.git

from keras_vggface.vggface import VGGFace   
pretrained_model = VGGFace(model='resnet50', include_top=False, input_shape=(224, 224, 3), pooling='avg')  # pooling: None, avg or max
pretrained_model.summary()
pretrained_model.save("my_model.h5") #using h5 extension

输入层已连接。太糟糕了,这看起来很容易解决。 summary of the first few layers of the VGGface model


可能的解决方案

似乎可以使用TF 1.15.3来工作,我之前使用的是1.15.0。我会检查我是否偶然做了其他不同的事情。

1 个答案:

答案 0 :(得分:1)

失败的可能原因是模型的输入张量未连接到输出张量,即它们可能未使用。

这里是colab notebook,在此我重现了此错误。将笔记本电脑开头的io_type修改为tf.uint8,以查看与您遇到的错误类似的错误。

解决方案

您需要手动检查模型,并查看是否有任何悬空/丢失/未连接到输入的输入并将其删除。

发布模型链接,我也可以尝试对其进行调试。

相关问题