deeplab v3+ multi scales 代码解析

multi scale能够大大增加识别率,简单直白的说就是将图片resize,然后预测。

只能在eval时使用,所以不需要训练

可用范围: [0.5, 0.75, 1.0, 1.25, 1.5, 1.75] ,定义在eval。py中

# Change to [0.5, 0.75, 1.0, 1.25, 1.5, 1.75] for multi-scale test.
flags.DEFINE_multi_float('eval_scales', [0.25,0.5,1.75],
                         'The scales to resize images for evaluation.')

官方使用

全部 [0.5, 0.75, 1.0, 1.25, 1.5, 1.75] 阔怕,真的是有设备啊,哭,我给出尺度以及图片大小对照表,原始图片大小是513,513,3:

1.75:(897,897,3)

1.5: (769,769,3)

1.25: (641,641,3)

 

具体处理代码肯定是在model。py里面。

eval.py(main)->model.py(predict_labels_multi_scale)

model.py:

predict_labels_multi_scale->multi_scale_logits

  1. 在predict_labels_multi_scale中,对每个scale都利用multi_scale_logit进行多尺度预测,返回的是放缩后的预测logit,比如,21类,原始图像513*513, logit.shape=(?,129,129,21).
  2. 对该logit的bilinear放缩,到原始大小
  3. 收集得到的所有不同尺度input的相同大小logit到list outputs_to_predictions当中。
  4. 需要注意的是这里还有flip的选择问题,目前如果不主动使用--add_flipped_images=True的话,是不会主动进行flip的

细看代码

  for i, image_scale in enumerate(eval_scales):
    with tf.variable_scope(tf.get_variable_scope(), reuse=True if i else None):
      outputs_to_scales_to_logits = multi_scale_logits(
          images,
          model_options=model_options,
          image_pyramid=[image_scale],
          is_training=False,
          fine_tune_batch_norm=False)

可以看出来,这里是逐个处理scale的。传递近multi_scale_logits里面的是单一的数值比如0.25.

原始图片的放缩在model.multi_scale_logits里,使用bilinear进行放缩:

    if image_scale != 1.0:
      scaled_height = scale_dimension(crop_height, image_scale)
      scaled_width = scale_dimension(crop_width, image_scale)
      scaled_crop_size = [scaled_height, scaled_width]
      scaled_images = _resize_bilinear(images, scaled_crop_size, images.dtype)
     
      if model_options.crop_size:
        scaled_images.set_shape(
            [None, scaled_height, scaled_width, num_channels])
  
      # Adjust image_pooling_crop_size accordingly.
      scaled_image_pooling_crop_size = None
      if model_options.image_pooling_crop_size:
        scaled_image_pooling_crop_size = [
            scale_dimension(image_pooling_crop_height, image_scale),
            scale_dimension(image_pooling_crop_width, image_scale)]
image_pooling_crop_size会被赋值成 scaled_image_pooling_crop_size,目前是None

放缩后的图片经过model._get_logit后,将会得到相应尺度的特征图,比如0.25对应的是(?,129,129,channels)的特征图。

然后回到model.predict_labels_multi_scale使用_resize_bilinear进行放缩回原来的尺寸:

    for output in sorted(outputs_to_logits):

      outputs_to_logits[output] = _resize_bilinear(
          outputs_to_logits[output], [logits_height, logits_width],
          outputs_to_logits[output].dtype)

之后都存储在scales_to_logits 这是个list,熟悉的append

    for output in sorted(outputs_to_scales_to_logits):
      scales_to_logits = outputs_to_scales_to_logits[output]
      logits = _resize_bilinear(
          scales_to_logits[MERGED_LOGITS_SCOPE],
          tf.shape(images)[1:3],
          scales_to_logits[MERGED_LOGITS_SCOPE].dtype)
      outputs_to_predictions[output].append(
          tf.expand_dims(tf.nn.softmax(logits), 4))

在累积了大量tensor之后其实也不多,将他们concatenate:

  for output in sorted(outputs_to_predictions):
    predictions = outputs_to_predictions[output]
    # Compute average prediction across different scales and flipped images.
    predictions = tf.reduce_mean(tf.concat(predictions, 4), axis=4)
    outputs_to_predictions[output] = tf.argmax(predictions, 3)

然后给出预测。

 

你可能感兴趣的:(deeplabv3+)