Der*_*k_M 5 python serialization keras tensorflow
我见过这个问题的不同版本,但我还没有找到令人满意的答案。基本上,我想做从 keras model.to_json()、model.get_weights()、model.from_json()、model.set_weights()到tensorflow 的等效操作。我想我已经接近目标了,但我却陷入了困境。我更希望能够在同一个字符串中获得权重和图表,但我知道这是否不可能。
目前,我所拥有的是:
g = optimizer.minimize(loss_op,
global_step=tf.train.get_global_step())
de = g.graph.as_graph_def()
json_string = json_format.MessageToJson(de)
gd = tf.GraphDef()
gd = json_format.Parse(json_string, gd)
Run Code Online (Sandbox Code Playgroud)
这似乎很好地创建了图,但显然元图不包含变量、权重等。还有元图,但我唯一看到的是export_meta_graph,它似乎没有以相同的方式序列化。我看到 MetaGraph 有一个原型函数,但我不知道如何序列化这些变量。
简而言之,如何获取张量流模型(权重、图形等模型),将其序列化为字符串(最好是 json),然后反序列化并继续训练或提供预测。
以下是让我接近目标并且我已经尝试过的事情,但大多数情况下在需要写入磁盘方面都有限制,在这种情况下我无法做到这一点:
如果您想要keras Model.get_weights()和的等效项Model.set_weights(),这些方法与 keras 内部并没有紧密联系,并且可以轻松提取。
它们在 keras 源代码中的样子如下:
def get_weights(self):
weights = []
for layer in self.layers:
weights += layer.weights
return K.batch_get_value(weights) # this is just `get_session().run(weights)`
def set_weights(self, weights):
tuples = []
for layer in self.layers:
num_param = len(layer.weights)
layer_weights = weights[:num_param]
for sw, w in zip(layer.weights, layer_weights):
tuples.append((sw, w))
weights = weights[num_param:]
K.batch_set_value(tuples) # another wrapper over `get_session().run(...)`
Run Code Online (Sandbox Code Playgroud)
Kerasweights是 numpy 数组(不是 json)的列表。正如您所看到的,它利用了模型架构已知的事实 ( self.layers),这使得它能够重建从变量到值的正确映射。一些看似不平凡的工作是在 中完成的K.batch_set_value,但实际上它只是准备分配操作并在会话中运行它们。
def tensorflow_get_weights():
vars = tf.trainable_variables()
values = tf.get_default_session().run(vars)
return zip([var.name for var in vars], values)
def tensorflow_set_weights(weights):
assign_ops = []
feed_dict = {}
for var_name, value in weights:
var = tf.get_default_session().graph.get_tensor_by_name(var_name)
value = np.asarray(value)
assign_placeholder = tf.placeholder(var.dtype, shape=value.shape)
assign_op = tf.assign(var, assign_placeholder)
assign_ops.append(assign_op)
feed_dict[assign_placeholder] = value
tf.get_default_session().run(assign_ops, feed_dict=feed_dict)
Run Code Online (Sandbox Code Playgroud)
在这里,我假设您想要在默认会话中序列化/反序列化整个模型(即所有可训练变量)。如果不是这种情况,可以轻松定制上述功能。
x = tf.placeholder(shape=[None, 5], dtype=tf.float32, name='x')
W = tf.Variable(np.zeros([5, 5]), dtype=tf.float32, name='W')
b = tf.Variable(np.zeros([5]), dtype=tf.float32, name='b')
y = tf.add(tf.matmul(x, W), b)
with tf.Session() as session:
session.run(tf.global_variables_initializer())
# Save the weights
w = tensorflow_get_weights()
print(W.eval(), b.eval())
# Update the model
session.run([tf.assign(W, np.ones([5, 5])), tf.assign(b, np.ones([5]) * 2)])
print(W.eval(), b.eval())
# Restore the weights
tensorflow_set_weights(w)
print(W.eval(), b.eval())
Run Code Online (Sandbox Code Playgroud)
如果运行此测试,您应该会看到模型被冻结在零,然后更新,然后恢复到零。
| 归档时间: |
|
| 查看次数: |
6234 次 |
| 最近记录: |