目前,我正在Tf-Slim库中使用预训练的VGG模型。我的动机是为这个netowrk生成给定图像的对抗性示例。任务摘要是:
x= tf.placeholder(shape=(None, 32, 32,3), dtype=tf.float32)
for i in range(2):
logits= vgg.vgg_16(x, is_training=False, spatial_squeeze=False, fc_conv_padding='SAME')
x = x + learning_rate*cal_gradient_of_logits_wrt_x(logits)
然而,一旦我们进入第二次迭代并开始运行logits = vgg.vgg16(....),我们会收到以下错误:
Variable vgg_16/conv1/conv1_1/weights already exists, disallowed. Did you mean to set reuse=True or reuse=tf.AUTO_REUSE in VarScope?
很明显,由于在第二次迭代中复制了图形而发生了此错误。由于tf-slim模型在范围中没有使用reuse=True
,它会抛出此错误(因为在第二次迭代中我们再次要求它在图中添加已存在的vgg图层)。 / p>
有可能以某种方式避免此错误吗?应该可以为VGG模型创建一次图表,并在需要计算日志时使用它。
这应该是可能的原因是来自keras的例子。在keras中,我们可以使用
简单地定义模型model= vgg.VGG16(*args, *kwargs)
稍后,我们可以使用
添加不同张量的计算logitslogits_1= model(x1)
logits_2= model(x2)
现在在这两种计算中,将使用相同的模型参数,即不会出现这样的错误。有没有办法通过张量流模型实现相同的功能。
答案 0 :(得分:1)
在tfslim / models / research / slim / nets / vgg.py中:
在vgg16或vgg19定义中添加重用参数
def vgg_16(inputs,
num_classes=1000,
is_training=True,
dropout_keep_prob=0.5,
spatial_squeeze=True,
scope='vgg_16',
fc_conv_padding='VALID',
global_pool=False,
reuse=None):
... 然后设置变量作用域以在需要时重用arg_scope
with tf.variable_scope(scope, 'vgg_16', [inputs], reuse=reuse) as sc:
...
然后,当您调用函数时,将参数传递为reuse = tf.AUTO_REUSE
vgg.vgg_16(images, num_classes=dataset.num_classes,
is_training=True, reuse=tf.AUTO_REUSE)
答案 1 :(得分:0)
您可以使用tf.make_template(func)执行此操作。
x= tf.placeholder(shape=(None, 32, 32,3), dtype=tf.float32)
vgg_model = tf.make_template(vgg.vgg_16, is_training=False, spatial_squeeze=False, fc_conv_padding='SAME')
for i in range(2):
logits = vgg_model(x)
x += learning_rate*cal_gradient_of_logits_wrt_x(logits)