As a newbie, I wrote a custom function in octave to perform a 2D image convolution using separable kernels. The results of this custom function were compared with conv2() and they were consistent. But that was where the joy ended.
conv2() works at the speed of light while my custom function is slower than a steam locomotive.
How can I speed up the loops below? As you can see, the number of MACs per pixel is 6 compared to 9 that would have been the case in 2D convolution. The function takes as inputs a row vector(3x1) and a column vector(1x3).
function OutputImage = Convolve3X3(InputImage, RowCount, ColCount, Kernel_x, Kernel_y)
% Create a padded image
PaddedImage = uint8(zeros(RowCount + 2, ColCount + 2));
% Create a staging area
StagingImage = uint8(zeros(RowCount + 2, ColCount + 2));
% Create a Row Vector
RowVector = uint8(zeros(1,3));
% Create a Col Vector
ColVector = uint8(zeros(3,1));
% Copy the input image into the padded image
PaddedImage(2:RowCount + 1, 2:ColCount + 1) = InputImage;
% 1D convolution of necessary rows with Kernel_x
for i = 2: RowCount + 1
for j = 1:ColCount
RowVector = PaddedImage(i,j:j+2) .* Kernel_x;
StagingImage(i,j) = RowVector(1) + RowVector(2) + RowVector(3);
end
end
% 1D convolution of necessary columns with Kernel_y
for i = 1: RowCount
for j = 1:ColCount
ColVector = StagingImage(i:i+2,j) .* Kernel_y;
OutputImage(i,j) = ColVector(1) + ColVector(2) + ColVector(3);
end
end
endfunction
How is conv2() so radically fast?