【问题标题】:Caffe test net with images as labels以图像为标签的 Caffe 测试网
【发布时间】:2018-05-17 16:42:38
【问题描述】:

问题

我尝试创建一个使用图像作为标签的 CNN,其值介于 0 和 1 之间。经过一些训练后,我的网络损失了大约 23 轮。现在我想看看结果。为此,我正在使用这个 python 脚本:

import caffe
import numpy as np
from PIL import Image

net = caffe.Net('D:/caffe/net.prototxt',
            'D:/caffe/net_iter_35000.caffemodel',
            caffe.TEST)

# load input and configure preprocessing
transformer = caffe.io.Transformer({'data': net.blobs['data'].data.shape})

transformer.set_mean('data', np.load('train_mean.npy').mean(1).mean(1))
transformer.set_transpose('data', (2,0,1))
transformer.set_channel_swap('data', (2,1,0))
transformer.set_raw_scale('data', 255.0)

#note we can change the batch size on-the-fly 
#since we classify only one image, we change batch size from 10 to 1
net.blobs['data'].reshape(1,3,360,360)

#load the image in the data layer
im = caffe.io.load_image('train/img0.png')
net.blobs['data'].data[...] = transformer.preprocess('data', im)

#compute
out = net.forward()

result = out['conv7'][0][0]

现在我预计 result 的值大约在 0 和 1 之间。但实际上 result.max() 返回 5.92,result.min() 返回 -4315.5。

python 脚本中是否有错误,或者这个值对于 23 的损失是否正常?


其他信息

我的 train_test.prototxt:

layer {
  name: "mynet"
  type: "Data"
  top: "data0"
  top: "label0"
  include {
    phase: TRAIN
  }
  transform_param {
    mean_file: "train_mean.binaryproto"
    scale: 0.00390625
  }
  data_param {
    source: "train_lmdb"
    batch_size: 32
    backend: LMDB
  }
}

layer {
  name: "mynetlabel"
  type: "Data"
  top: "data1"
  top: "label1"
  include {
    phase: TRAIN
  }
  transform_param {
    scale: 0.00390625
  }
  data_param {
    source: "train_label_lmdb_2"
    batch_size: 32
    backend: LMDB
  }
}

layer {
  name: "mnist"
  type: "Data"
  top: "data0"
  top: "label0"
  include {
    phase: TEST
  }
  transform_param {
    mean_file: "train_mean.binaryproto"
    scale: 0.00390625
  }
  data_param {
    source: "val_lmdb"
    batch_size: 16
    backend: LMDB
  }
}
layer {
  name: "mnistlabel"
  type: "Data"
  top: "data1"
  top: "label1"
  include {
    phase: TEST
  }
  transform_param {
    scale: 0.00390625
  }
  data_param {
    source: "val_label_lmdb_2"
    batch_size: 16
    backend: LMDB
  }
}
.
. 
.
layer {
  name: "conv7"
  type: "Convolution"
  bottom: "conv6"
  top: "conv7"
  param {
    lr_mult: 5.0
    decay_mult: 1.0
  }
  param {
    lr_mult: 10.0
    decay_mult: 0.0
  }
  convolution_param {
    num_output: 1
    pad: 0
    kernel_size: 1
    weight_filler {
      type: "gaussian"
      std: 0.00999999977648
    }
    bias_filler {
      type: "constant"
    }
  }
}

layer {
  name: "accuracy"
  type: "Accuracy"
  bottom: "conv7"
  bottom: "data1"
  top: "accuracy"
  include {
    phase: TEST
  }
}

layer {
  name: "loss"
  type: "SigmoidCrossEntropyLoss"
  bottom: "conv7"
  bottom: "data1"
  top: "loss"
}

我的 net.prototxt:

layer {
  name: "data"
  type: "Input"
  top: "data"
  input_param { shape: { dim: 50 dim: 3 dim: 360 dim: 360 } }
  transform_param {
    scale: 0.00390625
  }
}
.
.
.
layer {
  name: "conv7"
  type: "Convolution"
  bottom: "conv6"
  top: "conv7"
  param {
    lr_mult: 5.0
    decay_mult: 1.0
  }
  param {
    lr_mult: 10.0
    decay_mult: 0.0
  }
  convolution_param {
    num_output: 1
    pad: 0
    kernel_size: 1
    weight_filler {
      type: "gaussian"
      std: 0.00999999977648
    }
    bias_filler {
      type: "constant"
    }
  }
}

【问题讨论】:

    标签: python neural-network computer-vision deep-learning caffe


    【解决方案1】:

    您的train_val.prototxt 使用"SigmoidWithCrossEntropy",正如该层的名称所暗示的那样,它(内部)包括"Sigmoid" 层和交叉熵损失。因此,在部署网络时,您应该在 net.prototxt 文件中将此层替换为 "Sigmoid" 层。
    详情请见this answer

    PS,
    caffe 不支持将"Accuracy" 层用于单个二进制输出:"Accuracy" 层假设您的预测维度等于类数(适用于"SoftmaxWithLoss")。在您的情况下,您有两个标签 {0, 1},但输出的暗淡仅为 1。有关详细信息,请参阅 this answer

    【讨论】:

    • 首先,Shai 你真棒。关于您的 PS:我使用图像作为标签,并且该图像中的多个位置可以是零和一之间的值(不仅仅是二进制零和一)。所以我猜这不是你所指的。您是否建议我使用 SoftmaxWithLoss 而不是 SigmoidWithCrossEntropy?还是我没有正确理解您的答案?
    • @SimpleNotGood 关于"Accuracy":您不能使用该层来测量单个输出预测的准确性。 Caffe 的"Accuracy" 层仅用于测量分类任务的准确性。要测量您的连续、单暗度预测的准确性,您需要使用不同的方法。
    • @SimpleNotGood 如果您的预测是 [0,1] 范围内的连续值,那么您似乎不需要使用 "Softmax" 而不是 "Sigmoid"
    • @SimpleNotGood 你有一个每像素 1dim 的预测。例如,在具有 80 个类的语义分割中,每像素有 80dim 预测。多维度预测是指通道维度,
    • @SimpleNotGood 假设是这样
    猜你喜欢
    • 2016-02-14
    • 2017-12-20
    • 2015-12-23
    • 2016-11-26
    • 2019-03-25
    • 1970-01-01
    • 2017-02-06
    • 2018-01-01
    • 1970-01-01
    相关资源
    最近更新 更多