@Paul Kuo, the problem is that graph has been saved in training mode. I think there is some placeholder similar to isTraining
that should be turned into False
before graph saving (note that it's about graph but not about checkpoint).
Moreover you may see some unusual transformations over input image.
May I ask you to try to find that isTraining
flag, set it to false and save the graph again by tf.train.write_graph
. Then freeze the same checkpoint files with new version of graph. Our first goal is emit train/test switches from the graph. Thank you!
UPDATE
@Paul Kuo, the following are steps to create a graph without training-testing switches. An extra steps are required to import it into OpenCV.
Step 1: Create a graph definition
Make a script with the following code at the root folder of Age-Gender-Estimate-TF.
import tensorflow as tf
import inception_resnet_v1
inp = tf.placeholder(tf.float32, shape=[None, 160, 160, 3], name='input_image')
age_logits, gender_logits, _ = inception_resnet_v1.inference(inp, keep_probability=0.8,
phase_train=False,
weight_decay=1e-5)
print age_logits # logits/age/BiasAdd
print gender_logits # logits/gender/BiasAdd
with tf.Session() as sess:
graph_def = sess.graph.as_graph_def()
tf.train.write_graph(graph_def, "", 'inception_resnet_v1.pb', as_text=False)
Here we create a graph definition for testing mode only (phase_train=False
).
Step 2: Freeze resulting graph with checkpoint.
python ~/tensorflow/tensorflow/python/tools/freeze_graph.py \
--input_graph=inception_resnet_v1.pb \
--input_checkpoint=savedmodel.ckpt \
--output_graph=frozen_inception_resnet_v1.pb \
--output_node_names="logits/age/BiasAdd,logits/gender/BiasAdd" \
--input_binary
Step 3: Checking
Using TensorBoard, check that our graph has no training subgraphs (compare with images above).
C:\fakepath\Screenshot from 2018-03-30 10-41-03.png
Step 4: Help OpenCV to import graph.
Unfortunately, current version of OpenCV cannot interpret this graph correctly because of single Reshape
layer that takes dynamically estimated target shape:
C:\fakepath\Screenshot from 2018-03-30 10-30-43.png
Actually, it's just a flattening that means reshaping from 4-dimensional blob to 2-dimensional keeping the same batch size. We replace manage it during graph definition because it's out of user's code:
# inception_resnet_v1.py, line 262:
net = slim.fully_connected(net, bottleneck_layer_size, activation_fn=None,
scope='Bottleneck', reuse=False)
But we can help OpenCV to manage it by modifying a text graph
.
Step 5: Create a text graph
import tensorflow as tf
# Read the graph.
with tf.gfile.FastGFile('frozen_inception_resnet_v1.pb') as f:
graph_def = tf.GraphDef()
graph_def.ParseFromString(f.read())
# Remove Const nodes.
for i in reversed(range(len(graph_def.node))):
if graph_def.node[i].op == 'Const':
del graph_def.node[i]
for attr in ['T', 'data_format', 'Tshape', 'N', 'Tidx', 'Tdim',
'use_cudnn_on_gpu', 'Index', 'Tperm', 'is_training',
'Tpaddings']:
if attr in graph_def.node[i].attr:
del graph_def.node[i].attr[attr]
# Save as text.
tf.train.write_graph(graph_def, "", "frozen_inception_resnet_v1.pbtxt", as_text=True)
Step 6: Modify a text graph
Remove the Shape
node
node {
name: "InceptionResnetV1/Bottleneck/BatchNorm/Shape"
op: "Shape"
input: "InceptionResnetV1/Bottleneck/MatMul"
attr {
key: "out_type"
value {
type: DT_INT32
}
}
}
Replace Reshape
to Identity
:
from
node {
name: "InceptionResnetV1/Bottleneck/BatchNorm/Reshape_1"
op: "Reshape"
input: "InceptionResnetV1/Bottleneck/BatchNorm/FusedBatchNorm"
input: "InceptionResnetV1/Bottleneck ...
(more)
@Paul Kuo, please attach a reference to a frozen graph.
Hi, dkurt, Thank you for your reply. The detail of getting the frozen graph is described below... .....
after loading the model, we perform some age-gendger detection and then save it again and is going to convet to a frozen graph
saver.save(sess, "./pbs/model_XXX.ckpt") #save to a check point
tf.train.write_graph(sess.graph_def, ".\pbs", "graphDef.pb", as_text=False) # saved in binary form
tf.train.write_graph(sess.graph_def, ".\pbs", "graphDef.pbtxt", as_text=True) # saved in text form .....
And then run freeze_graph.py (provided from tensorflow/python/tools) with the script below...
python freeze_graph.py --input_graph=./pbs/graphDef.pb --input_checkpoint=./pbs/model_XXX.ckpt --output_graph =./pbs/frozenGraph.pb --output_node_names=genderOut,ageOut --input_binary=true
then a frozenGraph.pb is generated.
Here you can download my generated "graphDef.pb" "graphDef.pbtxt" and "frozenGraph.pb" from https://www.dropbox.com/sh/l48teumzewpece8/AAA8T2brnQBnanh_gGMkY4Fra?dl=0 and see if anyone can figure out any error from it...
Thanks
Hi @dkurt, is there any luck to fix this problem...?
Everyone, any suggestions will be appreciated...
Thank you