I trained a yolov3 model (not the tiny version), and now I am trying to convert the saved yolo h5 file to Tensorflow pb, and so far I haven't had luck. This is how I am trying to do the conversion:
import tensorflow as tf
from tensorflow.python.framework import graph_io
from tensorflow.keras.models import load_model
# Clear any previous session.
tf.keras.backend.clear_session()
def freeze_graph(graph, session, output, save_pb_dir='.', save_pb_name='yoloModel.pb', save_pb_as_text=False):
with graph.as_default():
graphdef_inf = tf.graph_util.remove_training_nodes(graph.as_graph_def())
graphdef_frozen = tf.graph_util.convert_variables_to_constants(session, graphdef_inf, output)
graph_io.write_graph(graphdef_frozen, save_pb_dir, save_pb_name, as_text=save_pb_as_text)
return graphdef_frozen
tf.keras.backend.set_learning_phase(0)
model = load_model('yoloModel.h5')
session = tf.keras.backend.get_session()
INPUT_NODE = [t.op.name for t in model.inputs]
OUTPUT_NODE = [t.op.name for t in model.outputs]
print(INPUT_NODE, OUTPUT_NODE)
frozen_graph = freeze_graph(session.graph, session, [out.op.name for out in model.outputs], save_pb_dir=save_pb_dir)
I have seen other issues where people asked the same question and seems like some of them solved their problem. But I could not really understand some of the comments since they were in Chinese.
Could anyone who succeeded in converting the file, share his/her script?
Best,
Frank
@tiancailin I tried your suggestion, but I guess according to output h5 file does not have the model information?
(conda-tensorflow) C:\Users\Usr2192\Desktop\conversionTry\amir-abdi>python keras_to_tensorflow.py --input_model="trainedWeights.h5" --output_model="out.pb"
Using TensorFlow backend.
E0109 13:46:07.891747 12844 keras_to_tensorflow.py:95] Input file specified only holds the weights, and not the model definition. Save the model using model.save(filename.h5) which will contain the network architecture as well as its weights. If the model is saved using the model.save_weights(filename) function, either input_model_json or input_model_yaml flags should be set to to import the network architecture prior to loading the weights.
Check the keras documentation for more details (https://keras.io/getting-started/faq/)
Traceback (most recent call last):
File "keras_to_tensorflow.py", line 182, in <module>
app.run(main)
File "C:\Users\Usr2192\Anaconda3\envs\conda-tensorflow\lib\site-packages\absl\app.py", line 299, in run
_run_main(main, args)
File "C:\Users\Usr2192\Anaconda3\envs\conda-tensorflow\lib\site-packages\absl\app.py", line 250, in _run_main
sys.exit(main(argv))
File "keras_to_tensorflow.py", line 128, in main
model = load_model(FLAGS.input_model, FLAGS.input_model_json, FLAGS.input_model_yaml)
File "keras_to_tensorflow.py", line 106, in load_model
raise wrong_file_err
File "keras_to_tensorflow.py", line 63, in load_model
model = keras.models.load_model(input_model_path)
File "C:\Users\Usr2192\Anaconda3\envs\conda-tensorflow\lib\site-packages\keras\engine\saving.py", line 492, in load_wrapper
return load_function(*args, **kwargs)
File "C:\Users\Usr2192\Anaconda3\envs\conda-tensorflow\lib\site-packages\keras\engine\saving.py", line 584, in load_model
model = _deserialize_model(h5dict, custom_objects, compile)
File "C:\Users\Usr2192\Anaconda3\envs\conda-tensorflow\lib\site-packages\keras\engine\saving.py", line 270, in _deserialize_model
model_config = h5dict['model_config']
File "C:\Users\Usr2192\Anaconda3\envs\conda-tensorflow\lib\site-packages\keras\utils\io_utils.py", line 318, in __getitem__
raise ValueError('Cannot create group in read-only mode.')
ValueError: Cannot create group in read-only mode.
The program was worked fine,on my computer. I downloaded yolo's .weights file and converted it to .h5 file with convert.py, which can be converted to a .pb file.
how did you saved your .h5 file?model.save() or model.save_weights()?
Look's like the problem is "Cannot create group in read-only mode"??
I haven't modified the train.py and it uses model.save_weights()
I guess that's the problem?
I鈥榤 not sure.
Try train a model with 1 epoch and model.save() for test can or can't convert?
If on COCO dataset will waste you 2~3 hours.
I did that modification (model.save), and now I have the error saying that name 'yolo_head' is not defined.
To solve it, I tried importing the yolo_head by modifying how the model is loaded:
from yolo3.model import yolo_head
model = load_model('trainedWeights.h5', {'yolo_head': yolo_head})
but now I have the problem:
\yolo3\model.py", line 377, in yolo_loss
anchors[anchor_mask[l]], num_classes, input_shape, calc_loss=True)
TypeError: list indices must be integers or slices, not list
I wonder how the script found in here: https://github.com/amir-abdi/keras_to_tensorflow works directly for you :/
I did that modification (model.save), and now I have the error saying that name 'yolo_head' is not defined.
To solve it, I tried importing the yolo_head by modifying how the model is loaded:
from yolo3.model import yolo_head model = load_model('trainedWeights.h5', {'yolo_head': yolo_head})but now I have the problem:
\yolo3\model.py", line 377, in yolo_loss anchors[anchor_mask[l]], num_classes, input_shape, calc_loss=True) TypeError: list indices must be integers or slices, not listI wonder how the script found in here: https://github.com/amir-abdi/keras_to_tensorflow works directly for you :/
https://github.com/YunYang1994/tensorflow-yolov3
I think you can try this pure tensorflow version YOLOv3
@frankbrewer The model that you create for training is NOT the model that you want to use for inference. There seems to be an intermediate step of converting the weights from the trained model to the actual model. Once this is done you can convert, look here for more information https://github.com/qqwweee/keras-yolo3/issues/48
I am also in the same boat as you, trying to convert a model to tflite
I think you may need to try converting like this
from keras.models import Model
model = ... # create the original model
layer_name = 'my_layer'
intermediate_layer_model = Model(inputs=model.input,
outputs=model.get_layer(layer_name).output)
intermediate_output = intermediate_layer_model.predict(data)
can use my repository: https://github.com/nistarlwc/keras-yolo3-convert2pb