Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/tensorflow/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 在TF2.0中保存了_model.prune()_Python_Tensorflow_Tf.keras - Fatal编程技术网

Python 在TF2.0中保存了_model.prune()

Python 在TF2.0中保存了_model.prune(),python,tensorflow,tf.keras,Python,Tensorflow,Tf.keras,我正在尝试修剪使用tf.keras生成的SavedModel的节点。修剪脚本如下所示: svmod = tf.saved_model.load(fn) #version 1 #svmod = tfk.experimental.load_from_saved_model(fn) #version 2 feeds = ['foo:0'] fetches = ['bar:0'] svmod2 = svmod.prune(feeds=feeds, fetches=fetches) tf.saved_mo

我正在尝试修剪使用tf.keras生成的
SavedModel
的节点。修剪脚本如下所示:

svmod = tf.saved_model.load(fn) #version 1
#svmod = tfk.experimental.load_from_saved_model(fn) #version 2
feeds = ['foo:0']
fetches = ['bar:0']
svmod2 = svmod.prune(feeds=feeds, fetches=fetches)
tf.saved_model.save(svmod2, '/tmp/saved_model/') #version 1
#tfk.experimental.export_saved_model(svmod2, '/tmp/saved_model/') #version 2
如果我使用版本#1,则修剪工作正常,但在保存时提供了
ValueError:导出时需要一个可跟踪对象。在版本2中,没有prune()方法


如何修剪TF2.0 Keras SavedModel?

由于您可以在版本1中成功地修剪,我建议您尝试使用“pickle”来保存模型。 请尝试以下步骤以保存模型

import pickle
with open('<model_name.pkl>', 'wb') as f:
    pickle.dump(<your_model>, f)
导入pickle
将open(“”,'wb')作为f:
pickle.dump(,f)
将模型解读为:

with open('<model_name.pkl>', 'rb') as f:
    model = pickle.load(f)
以open(“”,'rb')作为f:
模型=pickle.load(f)

在您的情况下,对于版本1,您的代码片段中的#u模型是svmod2看起来您在版本1中修剪模型的方式很好;根据错误消息,生成的修剪模型无法保存,因为它不“可跟踪”,这是使用
tf.saved\u model.save
保存模型的必要条件。制作可跟踪对象的一种方法是从类继承,如和指南中所述。下面是尝试保存对象(由于对象不可跟踪而失败)、从
tf.module
继承并保存结果对象的示例:

(使用Python版本3.7.6、TensorFlow版本2.1.0和NumPy版本1.18.1)

导入tensorflow作为tf,numpy作为np
#定义一个随机张量流函数并生成一个参考输出
conv_filter=tf.random.normal([1,2,4,2],seed=1254)
@功能
def conv_型号(x):
返回tf.nn.conv2d(x,conv_过滤器,1,“相同”)
输入张量=tf.one([1,2,3,4])
输出张量=转换模型(输入张量)
打印(“原始模型输出:”,输出张量,sep=“\n”)
#尝试保存模型:它不会工作,因为tf.function不可跟踪
export_dir=“/tmp/”
try:tf.saved\u model.save(conv\u model,export\u dir)
除了值错误:打印(
“无法保存{}对象,因为它不可跟踪”。格式(类型(conv_model)))
#现在通过从tf.Module类继承来定义一个可跟踪对象
类MyModule(tf.Module):
@功能
定义调用(self,x):返回conv_模型(x)
#实例化可跟踪对象,并调用一次以跟踪编译图形
模块_func=MyModule()
模函数(输入张量)
tf.saved\u model.save(模块函数,导出目录)
#恢复模型并验证输出是否一致
还原的模型=tf.saved\u model.load(导出目录)
恢复的\输出\张量=恢复的\模型(输入\张量)
打印(“恢复的模型输出:”,恢复的输出张量,sep=“\n”)
如果np.array_等于(output_tensor.numpy(),则还原的_output_tensor.numpy()):
打印(“输出一致:)”)
其他:打印(“输出不一致:(”)
控制台输出:

原始模型输出:
tf张量(
[[[[-2.3629642   1.2904963 ]
[-2.3629642   1.2904963 ]
[-0.02110204  1.3400152 ]]
[[-2.3629642   1.2904963 ]
[-2.3629642   1.2904963 ]
[-0.021104 1.3400152]]],形状=(1,2,3,2),数据类型=float32)
无法保存对象
因为它不可追踪
恢复的模型输出:
tf张量(
[[[[-2.3629642   1.2904963 ]
[-2.3629642   1.2904963 ]
[-0.02110204  1.3400152 ]]
[[-2.3629642   1.2904963 ]
[-2.3629642   1.2904963 ]
[-0.021104 1.3400152]]],形状=(1,2,3,2),数据类型=float32)
输出一致:)
因此,您应该尝试按如下方式修改代码:

svmod = tf.saved_model.load(fn) #version 1
#svmod = tfk.experimental.load_from_saved_model(fn) #version 2
feeds = ['foo:0']
fetches = ['bar:0']
svmod2 = svmod.prune(feeds=feeds, fetches=fetches)
tf.saved_model.save(svmod2, '/tmp/saved_model/') #version 1
#tfk.experimental.export_saved_model(svmod2, '/tmp/saved_model/') #version 2
svmod=tf.saved_model.load(fn)#版本1
svmod2=svmod.prune(feeds=['foo:0'],fetches=['bar:0'])
类可导出(tf.Module):
@功能
定义调用(自身、模型输入):返回svmod2(模型输入)
svmod2_导出=可导出()
svmod2_导出(典型输入)#使用典型输入调用一次以跟踪编译
tf.saved_model.save(svmod2_导出“/tmp/saved_model/”)
如果您不想从
tf.Module
继承,您也可以只实例化
tf.Module
对象,并通过替换该部分代码添加
tf.function
方法/可调用属性,如下所示:

svmod = tf.saved_model.load(fn) #version 1
#svmod = tfk.experimental.load_from_saved_model(fn) #version 2
feeds = ['foo:0']
fetches = ['bar:0']
svmod2 = svmod.prune(feeds=feeds, fetches=fetches)
tf.saved_model.save(svmod2, '/tmp/saved_model/') #version 1
#tfk.experimental.export_saved_model(svmod2, '/tmp/saved_model/') #version 2
to_export=tf.Module()
to_export.call=tf.function(conv_模型)
调用(输入张量)
tf.saved\u model.save(to\u export,export\u dir)
还原的模块=tf.saved\u model.load(导出目录)
restored\u func=restored\u module.call

很抱歉,我不清楚是否需要使用TF SavedModel格式,这是TF serving、TFLite等的标准格式。保存在pickle文件中并不能实现这一点。这非常有用,但我遇到了一个问题。我的模型是带有估计器的trainer,它似乎输入了
全局步骤
。同样地,当尝试执行上述操作时,我得到一个错误:
TypeError:预期的参数名称为['Placeholder','global_step',],但得到了['Placeholder'的值。缺少:['global_step']。
实际上,我通过在调用函数定义中手动传递一个全局步骤来修复这个问题。然而,当尝试加载时,我得到了错误:
File”/usr/local/lib/python3.7/site packages/tensorflow/python/keras/saving/saving/saving\u utils.py“,第113行,在跟踪模型调用(model.call,def\u function.function)中,如果是instance(model.call,def\u function.function):AttributeError:“\u UserObject”对象没有属性“call”
Hmm。。。你能发布完整的代码和错误信息吗?可能作为一个新答案或新问题,在没有换行符的情况下阅读注释中的代码是很困难的。请将其单独发布在此处: