如何在 tensorFlow 中重用 slim.arg_scope?

Posted

技术标签:

【中文标题】如何在 tensorFlow 中重用 slim.arg_scope?【英文标题】:How to reuse slim.arg_scope in tensorFlow? 【发布时间】:2017-11-02 22:10:31 【问题描述】:

我正在尝试加载inception_resnet_v2_2016_08_30.ckpt 文件并进行测试。

该代码适用于单个图像(仅输入一次 oneFile() 函数)。

如果我调用 oneFile() 函数两次,会出现以下错误:

ValueError: 变量 InceptionResnetV2/Conv2d_1a_3x3/weights 已经 存在,不允许。您的意思是在 VarScope 中设置 reuse=True 吗? 最初定义于:

我在Sharing Variables找到了相关解决方案

如果tf.variable_scope遇到同样的问题,可以致电scope.reuse_variables()解决这个问题。

但我找不到slim.arg_scope 版本来重用范围。

def oneFile(filepath):
imgPath = filepath
testImage_string = tf.gfile.FastGFile(imgPath, 'rb').read()
testImage = tf.image.decode_jpeg(testImage_string, channels=3)
processed_image = inception_preprocessing.preprocess_image(testImage, image_size, image_size, is_training=False)
processed_images = tf.expand_dims(processed_image, 0)


# Create the model, use the default arg scope to configure the batch norm parameters.
with slim.arg_scope(inception_resnet_v2_arg_scope()):
    #logits, end_points = inception_resnet_v2(images, num_classes = dataset.num_classes, is_training = False)
    logits, _ = inception_resnet_v2(processed_images, num_classes=16, is_training=False)

probabilities = tf.nn.softmax(logits)

init_fn = slim.assign_from_checkpoint_fn(
    checkpoint_file,
    slim.get_model_variables(model_name))


with tf.Session() as sess:
    init_fn(sess)

    np_image, probabilities = sess.run([processed_images, probabilities])
    probabilities = probabilities[0, 0:]
    sorted_inds = [i[0] for i in sorted(enumerate(-probabilities), key=lambda x: x[1])]
    #print(probabilities)
    print(probabilities.argmax(axis=0))
    #names = imagenet.create_readable_names_for_imagenet_labels()
    #for i in range(15):
    #    index = sorted_inds[i]
    #    print((probabilities[index], names[index]))

def main():
for image_file in os.listdir(dataset_dir):
    try:
        image_type = imghdr.what(os.path.join(dataset_dir, image_file))
        if not image_type:
            continue
    except IsADirectoryError:
        continue

    #image = Image.open(os.path.join(dataset_dir, image_file))
    filepath = os.path.join(dataset_dir, image_file)

    oneFile(filepath)

inception_resnet_v2_arg_scope

def inception_resnet_v2_arg_scope(weight_decay=0.00004,
                                  batch_norm_decay=0.9997,
                                  batch_norm_epsilon=0.001):
  """Yields the scope with the default parameters for inception_resnet_v2.

  Args:
    weight_decay: the weight decay for weights variables.
    batch_norm_decay: decay for the moving average of batch_norm momentums.
    batch_norm_epsilon: small float added to variance to avoid dividing by zero.

  Returns:
    a arg_scope with the parameters needed for inception_resnet_v2.
  """
  # Set weight_decay for weights in conv2d and fully_connected layers.
  with slim.arg_scope([slim.conv2d, slim.fully_connected],
                      weights_regularizer=slim.l2_regularizer(weight_decay),
                      biases_regularizer=slim.l2_regularizer(weight_decay)):

    batch_norm_params = 
        'decay': batch_norm_decay,
        'epsilon': batch_norm_epsilon,
    
    # Set activation_fn and parameters for batch_norm.
    with slim.arg_scope([slim.conv2d], activation_fn=tf.nn.relu,
                        normalizer_fn=slim.batch_norm,
                        normalizer_params=batch_norm_params) as scope:

      return scope

完整的错误信息:

./data/test/teeth/1/7070.jpg Traceback(最近一次通话最后):文件 “testing.py”,第 111 行,在 main() 文件“testing.py”,第 106 行,在 main cal(processed_images) 文件“testing.py”,第 67 行,在 cal logits, _ = inception_resnet_v2(processed_images, num_classes=16, is_training=False) 文件 “/notebooks/transfer_learning_tutorial/inception_resnet_v2.py”,行 123,在 inception_resnet_v2 范围='Conv2d_1a_3x3')文件“/usr/local/lib/python3.5/dist-packages/tensorflow/contrib/framework/python/ops/arg_scope.py”, 第 181 行,在 func_with_args 返回 func(*args, **current_args) 文件 "/usr/local/lib/python3.5/dist-packages/tensorflow/contrib/layers/python/layers/layers.py", 第 918 行,在卷积中 输出= layer.apply(输入)文件“/usr/local/lib/python3.5/dist-packages/tensorflow/python/layers/base.py”, 第 320 行,申请中 return self.call(inputs, **kwargs) File "/usr/local/lib/python3.5/dist-packages/tensorflow/python/layers/base.py", 第 286 行,在 调用 self.build(input_shapes[0]) 文件“/usr/local/lib/python3.5/dist-packages/tensorflow/python/layers/convolutional.py”, 第 138 行,正在构建中 dtype=self.dtype) 文件 "/usr/local/lib/python3.5/dist-packages/tensorflow/python/ops/variable_scope.py", 第 1049 行,在 get_variable 中 use_resource=use_resource, custom_getter=custom_getter) 文件 "/usr/local/lib/python3.5/dist-packages/tensorflow/python/ops/variable_scope.py", 第 948 行,在 get_variable 中 use_resource=use_resource, custom_getter=custom_getter) 文件 "/usr/local/lib/python3.5/dist-packages/tensorflow/python/ops/variable_scope.py", 第 349 行,在 get_variable 中 validate_shape=validate_shape, use_resource=use_resource) 文件 "/usr/local/lib/python3.5/dist-packages/tensorflow/python/ops/variable_scope.py", 第 1389 行,在 Wrapped_custom_getter *args, **kwargs) 文件 "/usr/local/lib/python3.5/dist-packages/tensorflow/python/layers/base.py", 第 275 行,在 variable_getter 中 variable_getter=functools.partial(getter, **kwargs)) 文件“/usr/local/lib/python3.5/dist-packages/tensorflow/python/layers/base.py”, 第 228 行,在 _add_variable 中 trainable=trainable 和 self.trainable)文件“/usr/local/lib/python3.5/dist-packages/tensorflow/contrib/layers/python/layers/layers.py”, 第 1334 行,在 layer_variable_getter return _model_variable_getter(getter, *args, **kwargs) 文件“/usr/local/lib/python3.5/dist-packages/tensorflow/contrib/layers/python/layers/layers.py”, 第 1326 行,在 _model_variable_getter custom_getter=getter, use_resource=use_resource) 文件 "/usr/local/lib/python3.5/dist-packages/tensorflow/contrib/framework/python/ops/arg_scope.py", 第 181 行,在 func_with_args 返回 func(*args, **current_args) 文件“/usr/local/lib/python3.5/dist-packages/tensorflow/contrib/framework/python/ops/variables.py”, 第 262 行,在 model_variable 中 use_resource=use_resource) 文件 "/usr/local/lib/python3.5/dist-packages/tensorflow/contrib/framework/python/ops/arg_scope.py", 第 181 行,在 func_with_args 返回 func(*args, **current_args) 文件“/usr/local/lib/python3.5/dist-packages/tensorflow/contrib/framework/python/ops/variables.py”, 第 217 行,在变量中 use_resource=use_resource) 文件 "/usr/local/lib/python3.5/dist-packages/tensorflow/python/ops/variable_scope.py", 第 341 行,在 _true_getter use_resource=use_resource) 文件 "/usr/local/lib/python3.5/dist-packages/tensorflow/python/ops/variable_scope.py", 第 653 行,在 _get_single_variable 中 name, "".join(traceback.format_list(tb)))) ValueError: 变量 InceptionResnetV2/Conv2d_1a_3x3/weights 已经存在,不允许。 您的意思是在 VarScope 中设置 reuse=True 吗?最初定义于:

文件 “/usr/local/lib/python3.5/dist-packages/tensorflow/contrib/framework/python/ops/variables.py”, 第 217 行,在变量中 use_resource=use_resource) 文件 "/usr/local/lib/python3.5/dist-packages/tensorflow/contrib/framework/python/ops/arg_scope.py", 第 181 行,在 func_with_args 返回 func(*args, **current_args) 文件“/usr/local/lib/python3.5/dist-packages/tensorflow/contrib/framework/python/ops/variables.py”, 第 262 行,在 model_variable 中 使用资源=使用资源)

【问题讨论】:

【参考方案1】:

似乎tf.reset_default_graph() 在处理您的oneFile() 函数中的每个图像之前会解决这个问题,因为我在非常相似的示例代码中遇到了同样的问题。我的理解是,一旦将图像输入神经网络 (NN),由于 TensorFlow 使用了 variable scope 概念,需要告知变量可以重用,然后才能应用 NN到另一张图片。

【讨论】:

【参考方案2】:

我的猜测是您为图中的多个变量指定了相同的范围。当 tensorflow 在同一范围内找到多个变量时会发生此错误,而与下一张图像或下一批无关。创建图表时,您应该只考虑一个图像或批次来创建它。如果第一批或第一张图像一切正常,tensorflow 将负责下一次迭代,包括范围界定。

所以检查模型文件中的所有范围。我很确定您两次使用了相同的名称。

【讨论】:

以上是关于如何在 tensorFlow 中重用 slim.arg_scope?的主要内容,如果未能解决你的问题,请参考以下文章

Tensorflow在Python中导出和重用Estimator对象

在 Tensorflow 中重用层权重

tensorflow scope的作用

Tensorflow[LSTM]

Tensorflow LSTM实现

tensorflow-读写数据tf.data