This post follow the same idea as Lots of features from color histograms on a directory of images but using Edge orientation histograms in global and local features.
Basically I wanted to construct a collection of different edge orientation histograms for a collection of images that were saved in a directory. The histograms were calculated in different regions so I could get a lot of features. The images were numerated so the name of the file coincides with a number. The first thing I noticed was that I shouldn't use the code of Edge orientation histograms in global and local features directly because it was very inefficient. There is no need of calculating the gradients each time. It is better to do it just once and then extract the histogram from regions of this initial process. For this reason I divided that function in two functions: extract_edges and hist_edges. Here are both codes:
# parameters # - the image function [data] = extract_edges(im) % define the filters for the 5 types of edges f2 = zeros(3,3,5); f2(:,:,1) = [1 2 1;0 0 0;-1 -2 -1]; f2(:,:,2) = [-1 0 1;-2 0 2;-1 0 1]; f2(:,:,3) = [2 2 -1;2 -1 -1; -1 -1 -1]; f2(:,:,4) = [-1 2 2; -1 -1 2; -1 -1 -1]; f2(:,:,5) = [-1 0 1;0 0 0;1 0 -1]; % the size of the image ys = size(im,1); xs = size(im,2); # The image has to be in gray scale (intensities) if (isrgb(im)) im = rgb2gray(im); endif # Build a new matrix of the same size of the image # and 5 dimensions to save the gradients im2 = zeros(ys,xs,5); # iterate over the posible directions for i = 1:5 # apply the sobel mask im2(:,:,i) = filter2(f2(:,:,i), im); end # calculate the max sobel gradient [mmax, maxp] = max(im2,[],3); # save just the index (type) of the orientation # and ignore the value of the gradient im2 = maxp; # detect the edges using the default Octave parameters ime = edge(im, 'canny'); # multiply against the types of orientations detected # by the Sobel masks data = im2.*ime;
function [data] = histo_edges(im, edges, r) % size of the image ys = size(im,1); xs = size(im,2); size = round(ys/r) * round(xs/r); # produce a structur to save all the bins of the # histogram of each region eoh = zeros(r,r,6); # for each region for j = 1:r for i = 1:r # extract the subimage clip = edges(round((j-1)*ys/r+1):round(j*ys/r),round((i-1)*xs/r+1):round(i*xs/r)); # calculate the histogram for the region eoh(j,i,:) = (hist(makelinear(clip), 0:5)*100)/numel(clip); end end # take out the zeros eoh = eoh(:,:,2:6); # represent all the histograms on one vector data = zeros(1,numel(eoh)); data(:) = eoh(:);
Now, with this two functions and following the idea of Lots of features from color histograms on a directory of images, it is possible to generate the features in just one vector for each of the images:
function [t_set] = extract_eohs(dir, samples, filename) fibs = [1,2,3,5,8,13]; total = 0; ranges = [6, 2]; for fib = 1:size(fibs)(2) ranges(fib,1) = total + 1; total += 5*fibs(fib)*fibs(fib); ranges(fib,2) = total; endfor histo = zeros(samples, total); for ind = 1:samples im = imread(strcat(dir, int2str(ind))); edges = extract_edges(im); for fib = 1:size(fibs)(2) histo(ind,ranges(fib,1):ranges(fib,2)) = histo_edges(im, edges, fibs(fib)); endfor endfor save("-text", filename, "histo"); save("-text", "ranges.dat", "ranges"); t_set = ranges;