How to convolve two matrices with different sizes?
16 views (last 30 days)
Show older comments
I would like to filter a 2D image with a Gaussian by convolving them. The convolution must be done without using conv, conv2 ... functions.
The matrix image is not squared.
How could I implement this convolution?
Thanks in advanced
Help ASAP
5 Comments
Jonas
on 3 May 2021
Edited: Jonas
on 3 May 2021
Rep is you original image which is padded with 0 on all four sides of the image. it is padded about half height of k at bottom and top and about half width of k at the left and right. this is necessary because when you convolve, your signals become bigger compared to the original. it just like in 1d convolution if you convolve e.g. [1 2 3 4] with [3 8 5] the resulting signal will have length 6 which is longer than both input signals.
Answers (1)
DGM
on 3 May 2021
There's no reason to be looping over the kernel like that. Let's say you wanted to replicate the behavior of conv2:
inpict = im2double(rgb2gray(imread('peppers.png')));
fk=fkgen('gaussian',20); % filter kernel
example=conv2(inpict,fk); % example to test against
% get sizes
s0 = [size(inpict,1) size(inpict,2)];
sfk = [size(fk,1) size(fk,2)];
s = s0 + 2*(sfk-1);
% pad the array with zeros
padded = zeros(s);
padded(sfk(1):(end-sfk(1)+1),sfk(2):(end-sfk(2)+1)) = inpict;
% flip the kernel (this is convolution, not correlation)
fk = rot90(fk,2);
fk = fk(:);
% preallocate full-size output
% by default, conv2 does the same
outpict = zeros(sfk(1)+s0(1)-1,s0(2)+sfk(2)-1);
for m = 1:s(1)-sfk(1)+1
for n = 1:s(2)-sfk(2)+1
sample = padded(m:m+sfk(1)-1,n:n+sfk(2)-1);
outpict(m,n) = sample(:)'*fk;
end
end
% measure error between our method and conv2
immse(example,outpict)
If instead you wanted to work a bit more like imfilter(), there are some considerations
- By default, imfilter() zero-pads, but this causes vingetting. It's often desirable to use edge replication instead. You could use padarray() to do either.
- By default, imfilter() uses correlation, so the filter isn't rotated. For symmetric filters, there isn't a difference, but it's something to keep in mind if compatibility matters.
- By default, imfilter() returns the central area equal to the original image geometry. You'd just have to change the range of indices your filter slides over to change the output array. Otherwise you can just convolve the whole thing and crop off the excess.
0 Comments
See Also
Community Treasure Hunt
Find the treasures in MATLAB Central and discover how the community can help you!
Start Hunting!