18px;color:
#000000;">function F = hogcalculator1(img, cellpw, cellph, nblockw, nblockh, nthet, overlap, isglobalinterpolate, issigned, normmethod)
% IMG:
是输入图像, CELLPW和CELLPH分别是单元格像素宽度和高度。
% NBLOCKW、NBLCOKH:
分别是块中单元格在x和y方向上数量。
% NTHET:
是梯度方向直方图容器的数目
% ISSIGNED:
是梯度方向直方图范围从无符号的0到pi和有符号是0到2*pi条件。
可以通过设置变量的值ISSIGNED来指定。
% OVERLAP:
两个相邻块重叠的比例。
% ISGLOBALINTERPOLATE:
严格按照Dalal论文中程序要求来的。
% NORMMETHOD:
是块直方图归一化方法,设置为下列字符串:
‘none',这意味着非规范化;
% ’l1’,这意味着L1规范标准化;
% 'l2’,这意味着L2规范标准化;
% 'l1sqrt’,这意味着L1sqrt规范标准化;
% 'l2hys',这意味着L2-hys-norm标准化。
% F:
是一个行向量,存储所有块的最后的直方图,从左上角到右下角一个一个扫描图像的方式,单元格的直方图以相同的方式存储在每个块中。
% 注意:
CELLPW*NBLOCKW 和 CELLPH*NBLOCKH 应该分别等于IMG的宽度和高度。
% 调用方式1:
这里是一个示范,在Dalal的论文中提到所有参数的设置最佳值是:
当窗口是128*64的大小(128行、64列)
% F = hogcalculator(window, 8, 8, 2, 2, 9, 0.5, 'localinterpolate', 'unsigned', 'l2hys');
% 调用方式2:
函数也可以像下面这样调用:
F = hogcalculator(window);其他参数的设置都通过使用上述dalal的提到的最佳值来默认。
%—————— 设置默认参数值。
if nargin < 2
cellpw = 8;
cellph = 8;
nblockw = 2;
nblockh = 2;
nthet = 9;
overlap = 0.5;
isglobalinterpolate = 'localinterpolate';
issigned = 'unsigned';
normmethod = 'l2hys';
else
if nargin < 10
error('Input parameters are not enough.');
end
end
% ——————检查参数的有效性。
[M, N, K] = size(img);
if mod(M,cellph*nblockh) ~= 0
error('IMG''s height should be an integral multiple of CELLPH*NBLOCKH.');
end
if mod(N,cellpw*nblockw) ~= 0
error('IMG''s width should be an integral multiple of CELLPW*NBLOCKW.');
end
if mod((1-overlap)*cellpw*nblockw, cellpw) ~= 0 ||...
mod((1-overlap)*cellph*nblockh, cellph) ~= 0
str1 = 'Incorrect OVERLAP or ISGLOBALINTERPOLATE parameter';
str2 = ', slide step should be an intergral multiple of cell size';
error([str1, str2]);
end
% 设置高斯空间权量窗口的标准偏差。
delta = cellpw*nblockw * 0.5;
% 计算梯度比例矩阵。
hx = [-1,0,1];
hy = -hx';
gradscalx = imfilter(double(img),hx);
gradscaly = imfilter(double(img),hy);
if K > 1
gradscalx = max(max(gradscalx(:
:
1),gradscalx(:
:
2)), gradscalx(:
:
3));
gradscaly = max(max(gradscaly(:
:
1),gradscaly(:
:
2)), gradscaly(:
:
3));
end
gradscal = sqrt(double(gradscalx.*gradscalx + gradscaly.*gradscaly));
% 计算梯度方向矩阵。
加上较小数值避免划分为零。
gradscalxplus = gradscalx+ones(size(gradscalx))*0.0001;
gradorient = zeros(M,N);
% 无符号的情况:
方向范围是0到pi。
if strcmp(issigned, 'unsigned') == 1
gradorient =...
atan(gradscaly./gradscalxplus) + pi/2;
or = 1;
else
%有符号的情况:
方向范围是0到2*pi。
if strcmp(issigned, 'signed') == 1
idx = find(gradscalx >= 0 & gradscaly >= 0);
gradorient(idx) = atan(gradscaly(idx)./gradscalxplus(idx));
idx = find(gradscalx < 0);
gradorient(idx) = atan(gradscaly(idx)./gradscalxplus(idx)) + pi;
idx = find(gradscalx >= 0 & gradscaly < 0);
gradorient(idx) = atan(gradscaly(idx)./gradscalxplus(idx)) + 2*pi;
or = 2;
else
error('Incorrect ISSIGNED parameter.');
end
end
% 计算块滑步。
xbstride = cellpw*nblockw*(1-overlap);
ybstride = cellph*nblockh*(1-overlap);
xbstridend = N - cellpw*nblockw + 1;
ybstridend = M - cellph*nblockh + 1;
% 计算在窗口检测到所有块的数量,这是ntotalbh*ntotalbw.
ntotalbh = ((M-cellph*nblockh)/ybstride)+1;
ntotalbw = ((N-cellpw*nblockw)/xbstride)+1;
% generate the matrix hist3dbig for storing the 3-dimensions histogram. the
% matrix covers the whole image in the 'globalinterpolate' condition or
% covers the local block in the 'localinterpolate' condition. The matrix is
% bigger than the area where it covers by adding additional elements
% (corresponding to the cells) to the surround for calculation convenience.
if strcmp(isglobalinterpolate, 'globalinterpolate') == 1
ncellx = N / cellpw;
ncelly = M / cellph;
hist3dbig = zeros(ncelly+2, ncellx+2, nthet+2);
F = zeros(1, (M/cellph-1)*(N/cellpw-1)*nblockw*nblockh*nthet);
glbalinter = 1;
else
if strcmp(isglobalinterpolate, 'localinterpolate') == 1
hist3dbig = zeros(nblockh+2, nblockw+2, nthet+2);
F = zeros(1, ntotalbh*ntotalbw*nblockw*nblockh*nthet);
glbalinter = 0;
else
error('Incorrect ISGLOBALINTERPOLATE parameter.')
end
end
% 生成矩阵来存储一个块的直方图;
sF = zeros(1, nblockw*nblockh*nthet);
% generate gaussian spatial weight.
[gaussx, gaussy] = meshgrid(0:
(cellpw*nblockw-1), 0:
(cellph*nblockh-1));
weight = exp(-((gaussx-(cellpw*nblockw-1)/2)...
.*(gaussx-(cellpw*nblockw-1)/2)+(gaussy-(cellph*nblockh-1)/2)...
.*(gaussy-(cellph*nblockh-1)/2))/(delta*delta));
% vote for histogram. there are two situations according to the interpolate
% condition('global' interpolate or local interpolate). The hist3d which is
% generated from the 'bigger' matrix hist3dbig is the final histogram.
if glbalinter == 1
xbstep = nblockw*cellpw;
ybstep = nblockh*cellph;
else
xbstep = xbstride;
ybstep = ybstride;
end
% block slide loop
for btly = 1:
ybstep:
ybstridend
for btlx = 1:
xbstep:
xbstridend
for bi = 1:
(cellph*nblockh)
for bj = 1:
(cellpw*nblockw)
i = btly + bi - 1;
j = btlx + bj - 1;
gaussweight = weight(bi,bj);
gs = gradscal(i,j);
go = gradorient(i,j);
if glbalinter == 1
jorbj = j;
iorbi = i;
else
jorbj = bj;
iorbi = bi;
end
% calculate bin index of hist3dbig
binx1 = floor((jorbj-1+cellpw/2)/cellpw) + 1;
biny1 = floor((iorbi-1+cellph/2)/cellph) + 1;
binz1 = floor((go+(or*pi/nthet)/2)/(or*pi/nthet)) + 1;
if gs == 0
continue;
end
binx2 = binx1 + 1;
biny2 = biny1 + 1;
binz2 = binz1 + 1;
x1 = (binx1-1.5)*cellpw + 0.5;
y1 = (biny1-1.5)*cellph + 0.5;
z1 = (binz1-1.5)*(or*pi/nthet);
% trilinear interpolation.
hist3dbig(biny1,binx1,binz1) =...
hist3dbig(biny1,binx1,binz1) + gs*gaussweight...
* (1-(jorbj-x1)/cellpw)*(1-(iorbi-y1)/cellph)...
*(1-(go-z1)/(or*pi/nthet));
hist3