简体   繁体   中英

How to make the output regression value in the range of [0,1], using MatConvNet?

I am trying to implement a regression using CNN, in which I input an image (RGB, 32x32x3) and the model can tell me a normalized value, eg, 0.711, that represents ratio of the area of the object in the image to the image size. In MatConvNet, I implemented the regression loss function as follows:

function Y = vl_l2normloss(X,c,dzdy)
assert(numel(X) == numel(c));
% n = sizer(X,1) * size(X,2);
n = size(X,4);
if nargin <= 2
  Y = sum((X(:) - c(:)).^2) ./ (2*n);
else
  assert(numel(dzdy) == 1);
  Y = reshape((dzdy / n) * (X(:) - c(:)), size(X));
end

And I also modified second last layer of the Cifar-10 network structure as below:

lr = [.1 2] ;

% Define network CIFAR10-quick
net.layers = {} ;

% Block 1
net.layers{end+1} = struct('type', 'conv', ...
                           'weights', {{0.01*randn(5,5,3,32, 'single'), zeros(1, 32, 'single')}}, ...
                           'learningRate', lr, ...
                           'stride', 1, ...
                           'pad', 2) ;
net.layers{end+1} = struct('type', 'pool', ...
                           'method', 'max', ...
                           'pool', [3 3], ...
                           'stride', 2, ...
                           'pad', [0 1 0 1]) ;
net.layers{end+1} = struct('type', 'relu') ;

% Block 2
net.layers{end+1} = struct('type', 'conv', ...
                           'weights', {{0.05*randn(5,5,32,32, 'single'), zeros(1,32,'single')}}, ...
                           'learningRate', lr, ...
                           'stride', 1, ...
                           'pad', 2) ;
net.layers{end+1} = struct('type', 'relu') ;
net.layers{end+1} = struct('type', 'pool', ...
                           'method', 'avg', ...
                           'pool', [3 3], ...
                           'stride', 2, ...
                           'pad', [0 1 0 1]) ; % Emulate caffe

% Block 3
net.layers{end+1} = struct('type', 'conv', ...
                           'weights', {{0.05*randn(5,5,32,64, 'single'), zeros(1,64,'single')}}, ...
                           'learningRate', lr, ...
                           'stride', 1, ...
                           'pad', 2) ;
net.layers{end+1} = struct('type', 'relu') ;
net.layers{end+1} = struct('type', 'pool', ...
                           'method', 'avg', ...
                           'pool', [3 3], ...
                           'stride', 2, ...
                           'pad', [0 1 0 1]) ; % Emulate caffe

% Block 4
net.layers{end+1} = struct('type', 'conv', ...
                           'weights', {{0.05*randn(4,4,64,64, 'single'), zeros(1,64,'single')}}, ...
                           'learningRate', lr, ...
                           'stride', 1, ...
                           'pad', 0) ;
net.layers{end+1} = struct('type', 'relu') ;

% Block 5
net.layers{end+1} = struct('type', 'conv', ...
                           'weights', {{0.05*randn(1,1,64,1, 'single'), zeros(1,1,'single')}}, ...
                           'learningRate', .1*lr, ...
                           'stride', 1, ...
                           'pad', 0) ;
% Loss layer
net.layers{end+1} = struct('type', 'l2normloss') ;

But the output regression value (when testing) are NOT in the range of [0,1]. I have no idea about why is this happened? Is there anything wrong in my setting? Thanks!

You can put a sigmoid function to your last layer or put sigmoid function after training.

like that net.layers{end}.type='sigmoid'; (I'm not sure this is written correctly)

or you can define manually. It gives you a number between 0 to 1.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM